diff --git a/VERSION b/VERSION
index 85e0458f69..68cb3479cc 100644
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-20.7
\ No newline at end of file
+20.7.1
\ No newline at end of file
diff --git a/api/v1/entries/execution.php b/api/v1/entries/execution.php
index 955750bb41..e07e6fd90d 100644
--- a/api/v1/entries/execution.php
+++ b/api/v1/entries/execution.php
@@ -122,7 +122,7 @@ class executionEntry extends entry
$useCode = $this->checkCodeUsed();
/* Set $_POST variables. */
$fields = 'project,name,begin,end,lifetime,desc,days,acl,status,PO,PM,QD,RD';
- if($useCode) $fields .= 'code';
+ if($useCode) $fields .= ',code';
$this->batchSetPost($fields, $oldExecution);
$this->setPost('whitelist', $this->request('whitelist', explode(',', $oldExecution->whitelist)));
diff --git a/api/v1/entries/executions.php b/api/v1/entries/executions.php
index 5ddc623228..420aa9fdab 100644
--- a/api/v1/entries/executions.php
+++ b/api/v1/entries/executions.php
@@ -81,7 +81,7 @@ class executionsEntry extends entry
$useCode = $this->checkCodeUsed();
$fields = 'project,name,begin,end,lifetime,desc,days,percent,parent';
- if($useCode) $fields .= 'code';
+ if($useCode) $fields .= ',code';
$this->batchSetPost($fields);
diff --git a/api/v1/entries/stories.php b/api/v1/entries/stories.php
index 8e41d74611..0a48253ab6 100644
--- a/api/v1/entries/stories.php
+++ b/api/v1/entries/stories.php
@@ -51,7 +51,7 @@ class storiesEntry extends entry
}
}
- $result[] = $this->format($story, 'openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList');
+ $result[] = $this->format($story, 'title:decodeHtml,openedBy:user,openedDate:time,assignedTo:user,assignedDate:time,reviewedBy:user,reviewedDate:time,lastEditedBy:user,lastEditedDate:time,closedBy:user,closedDate:time,deleted:bool,mailto:userList');
}
return $this->send(201, array('page' => $pager->pageID, 'total' => $pager->recTotal, 'limit' => $pager->recPerPage, 'stories' => $result, 'requirements' => $requirements));
}
diff --git a/bin/init.bat b/bin/init.bat
index 33132fbd89..855a3bf3a5 100644
--- a/bin/init.bat
+++ b/bin/init.bat
@@ -27,171 +27,7 @@ IF "%pmsRoot%"=="" (
:: get pmsRoot
if "%pmsRoot:~-1%" == "/" SET pmsRoot=%pmsRoot:~0,-1%
-:: get requestType
-SET requestType= 'PATH_INFO'
-for /f "tokens=3" %%f in ('find /c "'PATH_INFO'" "%baseDir%..\config\my.php"') do set count=%%f
-if not defined count set count=1
-if %count% == 0 SET requestType='GET'
-
-:: create ztcli
-SET ztcli= %phpcli% %baseDir%ztcli %%*
-echo %ztcli% > %baseDir%ztcli.bat
-echo ztcli.bat ok
-
-:: create backup.bat
-if %requestType% == 'PATH_INFO' (
- SET backup= %phpcli% %baseDir%ztcli "%pmsRoot%/backup-backup.html"
-)else (
- SET backup= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=backup&f=backup"
-)
-echo %backup% > %baseDir%backup.bat
-echo backup.bat ok
-
-:: create dailyreminder.bat
-if %requestType% == 'PATH_INFO' (
- SET computeburn= %phpcli% %baseDir%ztcli "%pmsRoot%/report-remind"
-)else (
- SET computeburn= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=report&f=remind"
-)
-echo %computeburn% > %baseDir%dailyreminder.bat
-echo dailyreminder.bat ok
-
-:: create computeburn.bat
-if %requestType% == 'PATH_INFO' (
- SET computeburn= %phpcli% %baseDir%ztcli "%pmsRoot%/execution-computeburn"
-)else (
- SET computeburn= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=execution&f=computeburn"
-)
-echo %computeburn% > %baseDir%computeburn.bat
-echo computeburn.bat ok
-
-:: create computetaskeffort.bat
-if %requestType% == 'PATH_INFO' (
- SET computetaskeffort= %phpcli% %baseDir%ztcli "%pmsRoot%/execution-computetaskeffort"
-)else (
- SET computetaskeffort= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=execution&f=computetaskeffort"
-)
-echo %computetaskeffort% > %baseDir%computetaskeffort.bat
-echo computetaskeffort.bat ok
-
-:: create checkdb.bat
-if %requestType% == 'PATH_INFO' (
- SET checkdb= %phpcli% %baseDir%ztcli "%pmsRoot%/admin-checkdb"
-)else (
- SET checkdb= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=admin&f=checkdb"
-)
-echo %checkdb% > %baseDir%checkdb.bat
-echo checkdb.bat ok
-
-:: create syncsvn.bat
-if %requestType% == 'PATH_INFO' (
- SET syncsvn= %phpcli% %baseDir%ztcli "%pmsRoot%/svn-run"
-)else (
- SET syncsvn= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=svn&f=run"
-)
-echo %syncsvn% > %baseDir%syncsvn.bat
-echo syncsvn.bat ok
-
-:: create syncgit.bat.
-if %requestType% == 'PATH_INFO' (
- SET syncgit= %phpcli% %baseDir%ztcli "%pmsRoot%/git-run"
-)else (
- SET syncgit= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=git&f=run"
-)
-echo %syncgit% > %baseDir%syncgit.bat
-echo syncgit.bat ok
-
-:: async send mail.
-if %requestType% == 'PATH_INFO' (
- SET sendmail= %phpcli% %baseDir%ztcli "%pmsRoot%/mail-asyncSend"
-)else (
- SET sendmail= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=mail&f=asyncSend"
-)
-echo %sendmail% > %baseDir%sendmail.bat
-echo sendmail.bat ok
-
-:: async send webhook.
-if %requestType% == 'PATH_INFO' (
- SET sendwebhook= %phpcli% %baseDir%ztcli "%pmsRoot%/webhook-asyncSend"
-)else (
- SET sendwebhook= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=webhook&f=asyncSend"
-)
-echo %sendwebhook% > %baseDir%sendwebhook.bat
-echo sendwebhook.bat ok
-
-:: create cycle todo.
-if %requestType% == 'PATH_INFO' (
- SET createcycle= %phpcli% %baseDir%ztcli "%pmsRoot%/todo-createCycle"
-)else (
- SET createcycle= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=todo&f=createCycle"
-)
-echo %createcycle% > %baseDir%createcycle.bat
-echo createcycle.bat ok
-
-:: init queue.
-if %requestType% == 'PATH_INFO' (
- SET initqueue= %phpcli% %baseDir%ztcli "%pmsRoot%/ci-initQueue"
-)else (
- SET initqueue= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=ci&f=initQueue"
-)
-echo %initqueue% > %baseDir%initqueue.bat
-echo initqueue.bat ok
-
-:: check build status.
-if %requestType% == 'PATH_INFO' (
- SET checkbuildstatus= %phpcli% %baseDir%ztcli "%pmsRoot%/ci-checkBuildStatus"
-)else (
- SET checkbuildstatus= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=ci&f=checkBuildStatus"
-)
-echo %checkbuildstatus% > %baseDir%checkbuildstatus.bat
-echo checkbuildstatus.bat ok
-
-:: execute compile.
-if %requestType% == 'PATH_INFO' (
- SET execcompile= %phpcli% %baseDir%ztcli "%pmsRoot%/ci-exec"
-)else (
- SET execcompile= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=ci&f=exec"
-)
-echo %execcompile% > %baseDir%execcompile.bat
-echo execcompile.bat ok
-
-:: delete log.
-if %requestType% == 'PATH_INFO' (
- SET deletelog= %phpcli% %baseDir%ztcli "%pmsRoot%/admin-deleteLog"
-)else (
- SET deletelog= %phpcli% %baseDir%ztcli "%pmsRoot%/index.php?m=admin&f=deleteLog"
-)
-echo %deletelog% > %baseDir%deletelog.bat
-echo deletelog.bat ok
-
-:: encrypt.
-if exist "%baseDir%php\encrypt.php" (
- SET encrypt= %phpcli% %baseDir%php\encrypt.php %%*
- echo %encrypt% > %baseDir%encrypt.bat
- echo encrypt.bat ok
-)
-
-:: create crond.bat
-SET cron= %phpcli% %baseDir%php\crond.php
-echo %cron% > %baseDir%crond.bat
-echo crond.bat ok
-
-:: create system cron.
-if not exist %cronDir% md %cronDir%
-echo # system cron. > %sysCron%
-echo #min hour day month week command. >> %sysCron%
-echo 0 1 * * * %baseDir%dailyreminder.bat # daily reminder. >> %sysCron%
-echo 1 1 * * * %baseDir%backup.bat # backup database and file. >> %sysCron%
-echo 1 23 * * * %baseDir%computeburn.bat # compute burndown chart. >> %sysCron%
-echo 1-59/2 * * * * %baseDir%syncsvn.bat # sync subversion. >> %sysCron%
-echo 1-59/2 * * * * %baseDir%syncgit.bat # sync git. >> %sysCron%
-echo 1-59/5 * * * * %baseDir%sendmail.bat # async send mail. >> %sysCron%
-echo 1-59/5 * * * * %baseDir%sendwebhook.bat # async send webhook. >> %sysCron%
-echo 1 1 * * * %baseDir%createcycle.bat # create cycle todo. >> %sysCron%
-echo 30 1 * * * %baseDir%deletelog.bat # delete log. >> %sysCron%
-echo 1 0 * * * %baseDir%initqueue.bat # init queue. >> %sysCron%
-echo 1-59/5 * * * * %baseDir%checkbuildstatus.bat # check build status. >> %sysCron%
-echo 1-59/5 * * * * %baseDir%execcompile.bat # execute compile. >> %sysCron%
+%phpcli% %baseDir%php\init.php %phpcli% %pmsRoot%
:: return 0 when success.
exit /b 0
diff --git a/bin/init.sh b/bin/init.sh
index 6af39a58a0..bb24596819 100755
--- a/bin/init.sh
+++ b/bin/init.sh
@@ -28,174 +28,7 @@ if [ ! -n "$2" ]; then
fi
pmsRoot=`echo "$pmsRoot" | sed 's/[/]$//g'`
-cat $basePath/../config/my.php |awk '$1!~/^\/\//&& $1~/\$config\->requestType/{requestType = $0} END{print requestType}'| grep -c 'PATH_INFO' > ./init.tmp
-if [ "`cat ./init.tmp`" != 0 ];then
- requestType='PATH_INFO';
-else
- requestType='GET';
-fi
-rm ./init.tmp
-
-# ztcli
-ztcli="$phpcli $basePath/ztcli \$*"
-echo $ztcli > $basePath/ztcli.sh
-echo "ztcli.sh ok"
-
-# backup database
-if [ $requestType == 'PATH_INFO' ]; then
- backup="$phpcli $basePath/ztcli '$pmsRoot/backup-backup.html'";
-else
- backup="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=backup&f=backup'";
-fi
-echo $backup > $basePath/backup.sh
-echo "backup.sh ok"
-
-# computeburn
-if [ $requestType == 'PATH_INFO' ]; then
- computeburn="$phpcli $basePath/ztcli '$pmsRoot/execution-computeburn'";
-else
- computeburn="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=execution&f=computeburn'";
-fi
-echo $computeburn > $basePath/computeburn.sh
-echo "computeburn.sh ok"
-
-# compute task effort.
-if [ $requestType == 'PATH_INFO' ]; then
- computetaskeffort="$phpcli $basePath/ztcli '$pmsRoot/execution-computetaskeffort'";
-else
- computetaskeffort="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=execution&f=computetaskeffort'";
-fi
-echo $computetaskeffort > $basePath/computetaskeffort.sh
-echo "computetaskeffort.sh ok"
-
-# daily remind
-if [ $requestType == 'PATH_INFO' ]; then
- checkdb="$phpcli $basePath/ztcli '$pmsRoot/report-remind'";
-else
- checkdb="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=report&f=remind'";
-fi
-echo $checkdb > $basePath/dailyreminder.sh
-echo "dailyreminder.sh ok"
-
-# check database
-if [ $requestType == 'PATH_INFO' ]; then
- checkdb="$phpcli $basePath/ztcli '$pmsRoot/admin-checkdb'";
-else
- checkdb="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=admin&f=checkdb'";
-fi
-echo $checkdb > $basePath/checkdb.sh
-echo "checkdb.sh ok"
-
-# syncsvn.
-if [ $requestType == 'PATH_INFO' ]; then
- syncsvn="$phpcli $basePath/ztcli '$pmsRoot/svn-run'";
-else
- syncsvn="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=svn&f=run'";
-fi
-echo $syncsvn > $basePath/syncsvn.sh
-echo "syncsvn.sh ok"
-
-# syncgit.
-if [ $requestType == 'PATH_INFO' ]; then
- syncgit="$phpcli $basePath/ztcli '$pmsRoot/git-run'";
-else
- syncgit="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=git&f=run'";
-fi
-echo $syncgit > $basePath/syncgit.sh
-echo "syncgit.sh ok"
-
-# async send mail.
-if [ $requestType == 'PATH_INFO' ]; then
- mailsend="$phpcli $basePath/ztcli '$pmsRoot/mail-asyncSend'";
-else
- mailsend="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=mail&f=asyncSend'";
-fi
-echo $mailsend > $basePath/sendmail.sh
-echo "sendmail.sh ok"
-
-# async send webhook.
-if [ $requestType == 'PATH_INFO' ]; then
- sendwebhook="$phpcli $basePath/ztcli '$pmsRoot/webhook-asyncSend'";
-else
- sendwebhook="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=webhook&f=asyncSend'";
-fi
-echo $sendwebhook > $basePath/sendwebhook.sh
-echo "sendwebhook.sh ok"
-
-# create cycle todo.
-if [ $requestType == 'PATH_INFO' ]; then
- createcycle="$phpcli $basePath/ztcli '$pmsRoot/todo-createCycle'";
-else
- createcycle="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=todo&f=createCycle'";
-fi
-echo $createcycle > $basePath/createcycle.sh
-echo "createcycle.sh ok"
-
-# init queue.
-if [ $requestType == 'PATH_INFO' ]; then
- initqueue="$phpcli $basePath/ztcli '$pmsRoot/ci-initQueue'";
-else
- initqueue="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=ci&f=initQueue'";
-fi
-echo $initqueue > $basePath/initqueue.sh
-echo "initqueue.sh ok"
-
-# check build status.
-if [ $requestType == 'PATH_INFO' ]; then
- checkbuildstatus="$phpcli $basePath/ztcli '$pmsRoot/ci-checkBuildStatus'";
-else
- checkbuildstatus="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=ci&f=checkBuildStatus'";
-fi
-echo $checkbuildstatus > $basePath/checkbuildstatus.sh
-echo "checkbuildstatus.sh ok"
-
-# execute compile.
-if [ $requestType == 'PATH_INFO' ]; then
- execcompile="$phpcli $basePath/ztcli '$pmsRoot/ci-exec'";
-else
- execcompile="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=ci&f=exec'";
-fi
-echo $execcompile > $basePath/execcompile.sh
-echo "execcompile.sh ok"
-
-# delete log.
-if [ $requestType == 'PATH_INFO' ]; then
- deletelog="$phpcli $basePath/ztcli '$pmsRoot/admin-deleteLog'";
-else
- deletelog="$phpcli $basePath/ztcli '$pmsRoot/index.php?m=admin&f=deleteLog'";
-fi
-echo $deletelog > $basePath/deletelog.sh
-echo "deletelog.sh ok"
-
-# encrypt.
-if [ -f "$basePath/php/encrypt.php" ]; then
- encrypt="$phpcli $basePath/php/encrypt.php \$*"
- echo $encrypt > $basePath/encrypt.sh
- echo "encrypt.sh ok"
-fi
-
-# cron
-if [ ! -d "$basePath/cron" ]; then
- mkdir $basePath/cron
-fi
-echo "# system cron." > $basePath/cron/sys.cron
-echo "#min hour day month week command." >> $basePath/cron/sys.cron
-echo "0 1 * * * $basePath/dailyreminder.sh # dailyreminder." >> $basePath/cron/sys.cron
-echo "1 1 * * * $basePath/backup.sh # backup database and file." >> $basePath/cron/sys.cron
-echo "1 23 * * * $basePath/computeburn.sh # compute burndown chart." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/syncsvn.sh # sync subversion." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/syncgit.sh # sync git." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/sendmail.sh # async send mail." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/sendwebhook.sh # async send webhook." >> $basePath/cron/sys.cron
-echo "1 1 * * * $basePath/createcycle.sh # create cycle todo." >> $basePath/cron/sys.cron
-echo "30 1 * * * $basePath/deletelog.sh # delete log." >> $basePath/cron/sys.cron
-echo "1 0 * * * $basePath/initqueue.sh # init queue." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/checkbuildstatus.sh # check build status." >> $basePath/cron/sys.cron
-echo "1-59/5 * * * * $basePath/execcompile.sh # execute compile." >> $basePath/cron/sys.cron
-cron="$phpcli $basePath/php/crond.php"
-echo $cron > $basePath/cron.sh
-echo "cron.sh ok"
-
+$phpcli "$basePath/php/init.php" $phpcli $pmsRoot;
chmod 755 $basePath/*.sh
exit 0
diff --git a/bin/php/init.php b/bin/php/init.php
new file mode 100644
index 0000000000..e3dd73c491
--- /dev/null
+++ b/bin/php/init.php
@@ -0,0 +1,65 @@
+config->requestType;
+$binPath = $basePath . '/bin';
+$crond = "# system cron.\n";
+$crond .= "#min \t hour \t day \t month \t week \t command.\n";
+
+/* Remove old cron. */
+foreach(glob("$binPath/*{$suffix}") as $file)
+{
+ $fileName = basename($file);
+ if($fileName == "init{$suffix}") continue;
+ unlink($file);
+}
+
+$crons = $app->dbh->query('SELECT * FROM ' . TABLE_CRON . " WHERE `type`='zentao' AND `status`='normal' AND `buildin`='1'")->fetchAll();
+foreach($crons as $cron)
+{
+ parse_str($cron->command, $params);
+ if(empty($params)) continue;
+
+ $command = '';
+ if($requestType == 'PATH_INFO')
+ {
+ $command = "$phpcli $binPath/ztcli '$pmsRoot/{$params['moduleName']}-{$params['methodName']}.html'";
+ }
+ else
+ {
+ $command = "$phpcli $binPath/ztcli '$pmsRoot/index.php?m={$params['moduleName']}&f={$params['methodName']}'";
+ }
+
+ $cronFile = strtolower($params['moduleName']) . strtolower($params['methodName']) . $suffix;
+ file_put_contents($binPath . '/' . $cronFile, $command);
+
+ $crond .= "{$cron->m} \t {$cron->h} \t {$cron->dom} \t {$cron->mon} \t {$cron->dow} \t $binPath/$cronFile \t #{$cron->remark}\n";
+ echo "{$cronFile} ok.\n";
+}
+
+if(!is_dir("$binPath/cron")) mkdir("$binPath/cron", 0777, true);
+file_put_contents("$binPath/cron/sys.cron", $crond);
+file_put_contents("$binPath/cron" . $suffix, "$phpcli $binPath/php/crond.php\n");
+echo "cron{$suffix} ok\n";
+
+file_put_contents("$binPath/ztcli{$suffix}", "$phpcli $binPath/ztcli " . ($suffix == '.bat' ? '%' : '$') . "*\n");
+echo "ztcli{$suffix} ok\n";
diff --git a/config/config.php b/config/config.php
index ae4719e8f6..3e8ef14524 100644
--- a/config/config.php
+++ b/config/config.php
@@ -16,7 +16,7 @@ if(!class_exists('config')){class config{}}
if(!function_exists('getWebRoot')){function getWebRoot(){}}
/* 基本设置。Basic settings. */
-$config->version = '20.7'; // ZenTaoPHP的版本。 The version of ZenTaoPHP. Don't change it.
+$config->version = '20.7.1'; // ZenTaoPHP的版本。 The version of ZenTaoPHP. Don't change it.
$config->liteVersion = '1.2'; // 迅捷版版本。 The version of Lite.
$config->charset = 'UTF-8'; // ZenTaoPHP的编码。 The encoding of ZenTaoPHP.
$config->cookieLife = time() + 2592000; // Cookie的生存时间。The cookie life time.
diff --git a/config/filter.php b/config/filter.php
index 5b063bc6f0..74d51b8fc2 100755
--- a/config/filter.php
+++ b/config/filter.php
@@ -398,6 +398,7 @@ $filter->testcase->browse->cookie['onlyScene'] = 'code';
$filter->todo->export->cookie['checkedItem'] = 'reg::checked';
$filter->user->login->cookie['keepLogin'] = 'equal::on';
+$filter->user->login->cookie['logout'] = 'equal::1';
$filter->user->export->cookie['checkedItem'] = 'reg::any';
$filter->block->default->get['hash'] = 'reg::md5';
diff --git a/config/zentaopms.php b/config/zentaopms.php
index 24a3a153af..d8f0e34978 100644
--- a/config/zentaopms.php
+++ b/config/zentaopms.php
@@ -714,6 +714,7 @@ $config->objectTables['market'] = TABLE_MARKET;
$config->objectTables['marketreport'] = TABLE_MARKETREPORT;
$config->objectTables['marketresearch'] = TABLE_PROJECT;
$config->objectTables['researchstage'] = TABLE_PROJECT;
+$config->objectTables['productline'] = TABLE_MODULE;
$config->newFeatures = array('introduction', 'tutorial', 'youngBlueTheme', 'visions', 'aiPrompts', 'promptDesign', 'promptExec');
$config->disabledFeatures = '';
diff --git a/db/standard/zentao20.7.1.sql b/db/standard/zentao20.7.1.sql
new file mode 100644
index 0000000000..d49e9c28d8
--- /dev/null
+++ b/db/standard/zentao20.7.1.sql
@@ -0,0 +1,4435 @@
+CREATE TABLE `zt_account` (
+ `id` smallint(5) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `provider` varchar(255) NOT NULL DEFAULT '',
+ `adminURI` varchar(255) NOT NULL DEFAULT '',
+ `account` varchar(255) NOT NULL DEFAULT '',
+ `password` varchar(255) NOT NULL DEFAULT '',
+ `email` varchar(255) NOT NULL DEFAULT '',
+ `mobile` varchar(255) NOT NULL DEFAULT '',
+ `extra` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `name` (`name`),
+ KEY `provider` (`provider`),
+ KEY `status` (`status`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_acl` (
+ `id` mediumint(9) NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `type` char(40) NOT NULL DEFAULT 'whitelist',
+ `source` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_action` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` text DEFAULT NULL,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `actor` varchar(100) NOT NULL DEFAULT '',
+ `action` varchar(80) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `comment` text DEFAULT NULL,
+ `extra` text DEFAULT NULL,
+ `read` enum('0','1') NOT NULL DEFAULT '0',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `efforted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `date` (`date`),
+ KEY `actor` (`actor`),
+ KEY `project` (`project`),
+ KEY `action` (`action`),
+ KEY `objectID` (`objectID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_actionrecent` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` text DEFAULT NULL,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `actor` varchar(100) NOT NULL DEFAULT '',
+ `action` varchar(80) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `comment` text DEFAULT NULL,
+ `extra` text DEFAULT NULL,
+ `read` enum('0','1') NOT NULL DEFAULT '0',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `efforted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `date` (`date`),
+ KEY `actor` (`actor`),
+ KEY `project` (`project`),
+ KEY `action` (`action`),
+ KEY `objectID` (`objectID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_activity` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `process` mediumint(9) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `optional` varchar(255) NOT NULL DEFAULT '',
+ `tailorNorm` varchar(255) NOT NULL DEFAULT '',
+ `content` mediumtext DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `order` mediumint(8) DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_assistant` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(30) NOT NULL,
+ `modelId` mediumint(8) unsigned NOT NULL,
+ `desc` text NOT NULL,
+ `systemMessage` text NOT NULL,
+ `greetings` text NOT NULL,
+ `icon` varchar(30) NOT NULL DEFAULT 'coding-1',
+ `enabled` enum('0','1') NOT NULL DEFAULT '1',
+ `createdDate` datetime NOT NULL,
+ `publishedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_message` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `appID` mediumint(8) unsigned NOT NULL,
+ `user` mediumint(8) unsigned NOT NULL,
+ `type` enum('req','res','ntf') NOT NULL,
+ `content` text NOT NULL,
+ `createdDate` datetime NOT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_miniprogram` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(30) NOT NULL,
+ `category` varchar(30) NOT NULL,
+ `desc` text DEFAULT NULL,
+ `model` mediumint(8) unsigned DEFAULT NULL,
+ `icon` varchar(30) NOT NULL DEFAULT 'writinghand-7',
+ `createdBy` varchar(30) NOT NULL,
+ `createdDate` datetime NOT NULL,
+ `editedBy` varchar(30) NOT NULL,
+ `editedDate` datetime NOT NULL,
+ `published` enum('0','1') NOT NULL DEFAULT '0',
+ `publishedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `prompt` text NOT NULL,
+ `builtIn` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_miniprogramfield` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `appID` mediumint(8) unsigned NOT NULL,
+ `name` varchar(30) NOT NULL,
+ `type` enum('radio','checkbox','text','textarea') DEFAULT 'text',
+ `placeholder` text DEFAULT NULL,
+ `options` text DEFAULT NULL,
+ `required` enum('0','1') DEFAULT '1',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_miniprogramstar` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `appID` mediumint(8) unsigned NOT NULL,
+ `userID` mediumint(8) unsigned NOT NULL,
+ `createdDate` datetime NOT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `appID` (`appID`,`userID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_model` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` varchar(20) NOT NULL,
+ `vendor` varchar(20) NOT NULL,
+ `credentials` text NOT NULL,
+ `proxy` text DEFAULT NULL,
+ `name` varchar(20) DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL,
+ `createdDate` datetime NOT NULL,
+ `editedBy` varchar(30) DEFAULT NULL,
+ `editedDate` datetime DEFAULT NULL,
+ `enabled` enum('0','1') NOT NULL DEFAULT '1',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_prompt` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(20) NOT NULL,
+ `desc` text DEFAULT NULL,
+ `model` mediumint(8) unsigned DEFAULT NULL,
+ `module` varchar(30) DEFAULT NULL,
+ `source` text DEFAULT NULL,
+ `targetForm` varchar(30) DEFAULT NULL,
+ `purpose` text DEFAULT NULL,
+ `elaboration` text DEFAULT NULL,
+ `role` text DEFAULT NULL,
+ `characterization` text DEFAULT NULL,
+ `status` enum('draft','active') NOT NULL DEFAULT 'draft',
+ `createdBy` varchar(30) NOT NULL,
+ `createdDate` datetime NOT NULL,
+ `editedBy` varchar(30) DEFAULT NULL,
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ai_promptrole` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(30) DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `model` mediumint(8) unsigned DEFAULT NULL,
+ `role` text DEFAULT NULL,
+ `characterization` text DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_api` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `product` varchar(255) NOT NULL DEFAULT '',
+ `lib` int(11) unsigned NOT NULL DEFAULT 0,
+ `module` int(11) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(100) NOT NULL DEFAULT '',
+ `path` varchar(255) NOT NULL DEFAULT '',
+ `protocol` varchar(10) NOT NULL DEFAULT '',
+ `method` varchar(10) NOT NULL DEFAULT '',
+ `requestType` varchar(100) NOT NULL DEFAULT '',
+ `responseType` varchar(100) NOT NULL DEFAULT '',
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '0',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `params` text DEFAULT NULL,
+ `paramsExample` text DEFAULT NULL,
+ `responseExample` text DEFAULT NULL,
+ `response` text DEFAULT NULL,
+ `commonParams` text DEFAULT NULL,
+ `addedBy` varchar(30) NOT NULL DEFAULT '0',
+ `addedDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_api_lib_release` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `lib` int(11) unsigned NOT NULL DEFAULT 0,
+ `desc` varchar(255) NOT NULL DEFAULT '',
+ `version` varchar(255) NOT NULL DEFAULT '',
+ `snap` mediumtext DEFAULT NULL,
+ `addedBy` varchar(30) NOT NULL DEFAULT '0',
+ `addedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_apispec` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `doc` int(11) unsigned NOT NULL DEFAULT 0,
+ `module` int(11) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(100) NOT NULL DEFAULT '',
+ `path` varchar(255) NOT NULL DEFAULT '',
+ `protocol` varchar(10) NOT NULL DEFAULT '',
+ `method` varchar(10) NOT NULL DEFAULT '',
+ `requestType` varchar(100) NOT NULL DEFAULT '',
+ `responseType` varchar(100) NOT NULL DEFAULT '',
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `owner` varchar(255) NOT NULL DEFAULT '0',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `params` text DEFAULT NULL,
+ `paramsExample` text DEFAULT NULL,
+ `responseExample` text DEFAULT NULL,
+ `response` text DEFAULT NULL,
+ `addedBy` varchar(30) NOT NULL DEFAULT '0',
+ `addedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_apistruct` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `lib` int(11) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(30) NOT NULL DEFAULT '',
+ `type` varchar(50) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `attribute` text DEFAULT NULL,
+ `addedBy` varchar(30) NOT NULL DEFAULT '0',
+ `addedDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_apistruct_spec` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(50) NOT NULL DEFAULT '',
+ `desc` varchar(255) NOT NULL DEFAULT '',
+ `attribute` text DEFAULT NULL,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `addedBy` varchar(30) NOT NULL DEFAULT '0',
+ `addedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approval` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `flow` mediumint(8) NOT NULL DEFAULT 0,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `nodes` mediumtext DEFAULT NULL,
+ `version` mediumint(9) NOT NULL DEFAULT 0,
+ `status` varchar(20) NOT NULL DEFAULT 'doing',
+ `result` varchar(20) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalflow` (
+ `id` int(11) NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `code` varchar(100) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `version` mediumint(8) NOT NULL DEFAULT 1,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `workflow` varchar(30) NOT NULL DEFAULT '',
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalflowobject` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `root` int(8) NOT NULL DEFAULT 0,
+ `flow` int(8) NOT NULL DEFAULT 0,
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `extra` varchar(255) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalflowspec` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `flow` mediumint(8) NOT NULL DEFAULT 0,
+ `version` mediumint(8) NOT NULL DEFAULT 0,
+ `nodes` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalnode` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `approval` mediumint(8) NOT NULL DEFAULT 0,
+ `type` enum('review','cc') NOT NULL DEFAULT 'review',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `account` char(30) NOT NULL DEFAULT '',
+ `node` varchar(100) NOT NULL DEFAULT '',
+ `reviewType` varchar(100) NOT NULL DEFAULT 'manual',
+ `agentType` varchar(100) NOT NULL DEFAULT 'pass',
+ `multipleType` enum('and','or') NOT NULL DEFAULT 'and',
+ `percent` smallint(6) NOT NULL DEFAULT 0,
+ `needAll` enum('0','1') NOT NULL DEFAULT '0',
+ `solicit` enum('0','1') NOT NULL DEFAULT '0',
+ `prev` mediumtext DEFAULT NULL,
+ `next` mediumtext DEFAULT NULL,
+ `status` varchar(20) NOT NULL DEFAULT 'wait',
+ `result` varchar(10) NOT NULL DEFAULT '',
+ `date` date DEFAULT NULL,
+ `opinion` mediumtext DEFAULT NULL,
+ `extra` mediumtext DEFAULT NULL,
+ `revertTo` char(30) NOT NULL DEFAULT '',
+ `forwardBy` char(30) NOT NULL DEFAULT '',
+ `reviewedBy` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `idx_reviewed_date` (`reviewedDate`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalobject` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `approval` int(8) NOT NULL DEFAULT 0,
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) NOT NULL DEFAULT 0,
+ `extra` varchar(255) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_approvalrole` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `code` char(30) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `users` longtext DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_artifactrepo` (
+ `id` smallint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(45) NOT NULL DEFAULT '',
+ `products` varchar(255) NOT NULL DEFAULT '',
+ `serverID` smallint(8) NOT NULL DEFAULT 0,
+ `repoName` varchar(45) NOT NULL DEFAULT '',
+ `format` varchar(10) NOT NULL DEFAULT '',
+ `type` char(7) NOT NULL DEFAULT '',
+ `status` varchar(10) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_assetlib` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_attend` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `date` date DEFAULT NULL,
+ `signIn` time DEFAULT NULL,
+ `signOut` time DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `ip` varchar(100) NOT NULL DEFAULT '',
+ `device` varchar(30) NOT NULL DEFAULT '',
+ `client` varchar(20) NOT NULL DEFAULT '',
+ `manualIn` time DEFAULT NULL,
+ `manualOut` time DEFAULT NULL,
+ `reason` varchar(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `reviewStatus` varchar(30) DEFAULT NULL,
+ `reviewedBy` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `attend` (`date`,`account`),
+ KEY `account` (`account`),
+ KEY `date` (`date`),
+ KEY `status` (`status`),
+ KEY `reason` (`reason`),
+ KEY `reviewStatus` (`reviewStatus`),
+ KEY `reviewedBy` (`reviewedBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_attendstat` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `month` char(10) NOT NULL DEFAULT '',
+ `normal` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `late` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `early` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `absent` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `trip` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `egress` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `lieu` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `paidLeave` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `unpaidLeave` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `timeOvertime` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `restOvertime` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `holidayOvertime` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `deserve` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `actual` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `status` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `attend` (`month`,`account`),
+ KEY `account` (`account`),
+ KEY `month` (`month`),
+ KEY `status` (`status`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_auditcl` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `model` char(30) NOT NULL DEFAULT 'waterfall',
+ `practiceArea` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `objectID` int(11) NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_auditplan` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `dateType` char(30) NOT NULL DEFAULT '',
+ `config` text DEFAULT NULL,
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `process` mediumint(9) NOT NULL DEFAULT 0,
+ `processType` char(30) NOT NULL DEFAULT '',
+ `checkDate` date DEFAULT NULL,
+ `checkedBy` varchar(30) NOT NULL DEFAULT '',
+ `realCheckDate` date DEFAULT NULL,
+ `result` char(30) NOT NULL DEFAULT '',
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `checkBy` varchar(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_auditresult` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `auditplan` mediumint(8) NOT NULL DEFAULT 0,
+ `listID` mediumint(8) NOT NULL DEFAULT 0,
+ `result` char(30) NOT NULL DEFAULT '',
+ `checkedBy` varchar(30) NOT NULL DEFAULT '',
+ `checkedDate` date DEFAULT NULL,
+ `comment` text DEFAULT NULL,
+ `severity` char(30) NOT NULL DEFAULT '',
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_automation` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `node` int(11) unsigned NOT NULL DEFAULT 0,
+ `product` int(11) unsigned NOT NULL DEFAULT 0,
+ `scriptPath` varchar(255) NOT NULL DEFAULT '',
+ `shell` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_basicmeas` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `purpose` varchar(50) NOT NULL DEFAULT '',
+ `scope` char(30) NOT NULL DEFAULT '',
+ `object` char(30) NOT NULL DEFAULT '',
+ `name` varchar(90) NOT NULL DEFAULT '',
+ `code` char(30) NOT NULL DEFAULT '',
+ `unit` varchar(100) NOT NULL DEFAULT '',
+ `configure` text DEFAULT NULL,
+ `params` text DEFAULT NULL,
+ `definition` text DEFAULT NULL,
+ `source` varchar(255) NOT NULL DEFAULT '',
+ `collectType` varchar(30) NOT NULL DEFAULT '',
+ `collectConf` text DEFAULT NULL,
+ `execTime` varchar(30) NOT NULL DEFAULT '',
+ `collectedBy` varchar(10) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `order` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `code` (`code`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_block` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `dashboard` varchar(20) NOT NULL DEFAULT '',
+ `module` varchar(20) NOT NULL DEFAULT '',
+ `title` varchar(100) NOT NULL DEFAULT '',
+ `block` varchar(30) NOT NULL DEFAULT '',
+ `code` varchar(30) NOT NULL DEFAULT '',
+ `width` enum('1','2','3') NOT NULL DEFAULT '1',
+ `height` smallint(6) unsigned NOT NULL DEFAULT 3,
+ `left` enum('0','1','2') NOT NULL DEFAULT '0',
+ `top` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `params` text DEFAULT NULL,
+ `hidden` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_branch` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `default` enum('0','1') NOT NULL DEFAULT '0',
+ `status` enum('active','closed') NOT NULL DEFAULT 'active',
+ `desc` varchar(255) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `closedDate` date DEFAULT NULL,
+ `order` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_budget` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `stage` char(30) NOT NULL DEFAULT '',
+ `subject` mediumint(8) NOT NULL DEFAULT 0,
+ `amount` char(30) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_bug` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `injection` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `identify` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `plan` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `storyVersion` smallint(6) NOT NULL DEFAULT 1,
+ `task` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `toTask` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `toStory` mediumint(8) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `severity` tinyint(4) NOT NULL DEFAULT 0,
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `os` varchar(255) NOT NULL DEFAULT '',
+ `browser` varchar(255) NOT NULL DEFAULT '',
+ `hardware` varchar(30) NOT NULL DEFAULT '',
+ `found` varchar(30) NOT NULL DEFAULT '',
+ `steps` mediumtext DEFAULT NULL,
+ `status` enum('active','resolved','closed') NOT NULL DEFAULT 'active',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `color` char(7) NOT NULL DEFAULT '',
+ `confirmed` tinyint(1) NOT NULL DEFAULT 0,
+ `activatedCount` smallint(6) NOT NULL DEFAULT 0,
+ `activatedDate` datetime DEFAULT NULL,
+ `feedbackBy` varchar(100) NOT NULL DEFAULT '',
+ `notifyEmail` varchar(100) NOT NULL DEFAULT '',
+ `mailto` text DEFAULT NULL,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `openedBuild` varchar(255) NOT NULL DEFAULT '',
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deadline` date DEFAULT NULL,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `resolution` varchar(30) NOT NULL DEFAULT '',
+ `resolvedBuild` varchar(30) NOT NULL DEFAULT '',
+ `resolvedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `duplicateBug` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `relatedBug` varchar(255) NOT NULL DEFAULT '',
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `caseVersion` smallint(6) NOT NULL DEFAULT 1,
+ `feedback` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `result` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `repo` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `mr` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `entry` text DEFAULT NULL,
+ `lines` varchar(10) NOT NULL DEFAULT '',
+ `v1` varchar(255) NOT NULL DEFAULT '',
+ `v2` varchar(255) NOT NULL DEFAULT '',
+ `repoType` varchar(30) NOT NULL DEFAULT '',
+ `issueKey` varchar(50) NOT NULL DEFAULT '',
+ `testtask` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `execution` (`execution`),
+ KEY `status` (`status`),
+ KEY `plan` (`plan`),
+ KEY `story` (`story`),
+ KEY `case` (`case`),
+ KEY `toStory` (`toStory`),
+ KEY `result` (`result`),
+ KEY `assignedTo` (`assignedTo`),
+ KEY `deleted` (`deleted`),
+ KEY `project` (`project`),
+ KEY `product_status_deleted` (`product`,`status`,`deleted`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_build` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` varchar(255) NOT NULL DEFAULT '0',
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `builds` varchar(255) NOT NULL DEFAULT '',
+ `name` char(150) NOT NULL DEFAULT '',
+ `scmPath` char(255) NOT NULL DEFAULT '',
+ `filePath` char(255) NOT NULL DEFAULT '',
+ `date` date DEFAULT NULL,
+ `stories` text DEFAULT NULL,
+ `bugs` text DEFAULT NULL,
+ `artifactRepoID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `builder` char(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `execution` (`execution`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_burn` (
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `task` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `date` date NOT NULL,
+ `estimate` float NOT NULL DEFAULT 0,
+ `left` float NOT NULL DEFAULT 0,
+ `consumed` float NOT NULL DEFAULT 0,
+ `storyPoint` float NOT NULL DEFAULT 0,
+ PRIMARY KEY (`execution`,`date`,`task`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_case` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `lib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(30) unsigned NOT NULL DEFAULT 0,
+ `storyVersion` smallint(6) NOT NULL DEFAULT 1,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `precondition` text DEFAULT NULL,
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 3,
+ `type` char(30) NOT NULL DEFAULT '1',
+ `auto` varchar(10) NOT NULL DEFAULT 'no',
+ `frame` varchar(10) NOT NULL DEFAULT '',
+ `stage` varchar(255) NOT NULL DEFAULT '',
+ `howRun` varchar(30) NOT NULL DEFAULT '',
+ `script` longtext DEFAULT NULL,
+ `scriptedBy` varchar(30) NOT NULL DEFAULT '',
+ `scriptedDate` date DEFAULT NULL,
+ `scriptStatus` varchar(30) NOT NULL DEFAULT '',
+ `scriptLocation` varchar(255) NOT NULL DEFAULT '',
+ `status` char(30) NOT NULL DEFAULT '1',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `color` char(7) NOT NULL DEFAULT '',
+ `frequency` enum('1','2','3') NOT NULL DEFAULT '1',
+ `order` tinyint(30) unsigned NOT NULL DEFAULT 0,
+ `openedBy` char(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `reviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `reviewedDate` date DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `version` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `linkCase` varchar(255) NOT NULL DEFAULT '',
+ `fromBug` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromCaseID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromCaseVersion` mediumint(8) unsigned NOT NULL DEFAULT 1,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `lastRunner` varchar(30) NOT NULL DEFAULT '',
+ `lastRunDate` datetime DEFAULT NULL,
+ `lastRunResult` char(30) NOT NULL DEFAULT '',
+ `scene` int(11) NOT NULL DEFAULT 0,
+ `sort` int(11) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `story` (`story`),
+ KEY `fromBug` (`fromBug`),
+ KEY `module` (`module`),
+ KEY `scene` (`scene`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_casestep` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `type` varchar(10) NOT NULL DEFAULT 'step',
+ `desc` text DEFAULT NULL,
+ `expect` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `case` (`case`),
+ KEY `version` (`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_cfd` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `execution` int(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ `name` char(30) NOT NULL DEFAULT '',
+ `count` smallint(6) NOT NULL DEFAULT 0,
+ `date` date DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `execution_type_name_date` (`execution`,`type`,`name`,`date`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_chart` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `code` varchar(255) NOT NULL DEFAULT '',
+ `driver` enum('mysql','duckdb') NOT NULL DEFAULT 'mysql',
+ `mode` enum('text','builder') NOT NULL DEFAULT 'builder',
+ `dimension` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `group` varchar(255) NOT NULL DEFAULT '',
+ `dataset` varchar(30) NOT NULL DEFAULT '0',
+ `desc` text DEFAULT NULL,
+ `acl` enum('open','private') NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `settings` mediumtext DEFAULT NULL,
+ `filters` mediumtext DEFAULT NULL,
+ `step` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `fields` mediumtext DEFAULT NULL,
+ `langs` text DEFAULT NULL,
+ `sql` mediumtext DEFAULT NULL,
+ `stage` enum('draft','published') NOT NULL DEFAULT 'draft',
+ `builtin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `objects` mediumtext DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_charter` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `level` int(8) NOT NULL DEFAULT 0,
+ `category` char(30) NOT NULL DEFAULT '',
+ `market` varchar(30) NOT NULL DEFAULT '',
+ `check` enum('0','1') NOT NULL DEFAULT '0',
+ `appliedBy` char(30) NOT NULL DEFAULT '',
+ `appliedDate` datetime DEFAULT NULL,
+ `budget` char(30) NOT NULL DEFAULT '',
+ `budgetUnit` char(30) NOT NULL DEFAULT '',
+ `product` text DEFAULT NULL,
+ `roadmap` text DEFAULT NULL,
+ `spec` mediumtext DEFAULT NULL,
+ `status` char(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `charterFiles` text DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(255) NOT NULL DEFAULT '',
+ `activatedBy` char(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `reviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `reviewedResult` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `meetingDate` date DEFAULT NULL,
+ `meetingLocation` varchar(255) NOT NULL DEFAULT '',
+ `meetingMinutes` mediumtext DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_cmcl` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` char(30) NOT NULL DEFAULT '',
+ `projectType` varchar(255) NOT NULL DEFAULT '',
+ `title` int(11) NOT NULL DEFAULT 0,
+ `contents` text DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `order` int(11) NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_company` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` char(120) DEFAULT NULL,
+ `phone` char(20) DEFAULT NULL,
+ `fax` char(20) DEFAULT NULL,
+ `address` char(120) DEFAULT NULL,
+ `zipcode` char(10) DEFAULT NULL,
+ `website` char(120) DEFAULT NULL,
+ `backyard` char(120) DEFAULT NULL,
+ `guest` enum('1','0') NOT NULL DEFAULT '0',
+ `admins` char(255) DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_compile` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `job` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `queue` mediumint(8) NOT NULL DEFAULT 0,
+ `status` varchar(255) NOT NULL DEFAULT '',
+ `logs` text DEFAULT NULL,
+ `atTime` varchar(10) NOT NULL DEFAULT '',
+ `testtask` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `tag` varchar(255) NOT NULL DEFAULT '',
+ `times` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `updateDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_config` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `vision` varchar(10) NOT NULL DEFAULT '',
+ `owner` char(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `section` char(30) NOT NULL DEFAULT '',
+ `key` char(30) NOT NULL DEFAULT '',
+ `value` longtext DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`vision`,`owner`,`module`,`section`,`key`),
+ KEY `vision` (`vision`),
+ KEY `owner` (`owner`),
+ KEY `module` (`module`),
+ KEY `key` (`key`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_cron` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `m` varchar(20) NOT NULL DEFAULT '',
+ `h` varchar(20) NOT NULL DEFAULT '',
+ `dom` varchar(20) NOT NULL DEFAULT '',
+ `mon` varchar(20) NOT NULL DEFAULT '',
+ `dow` varchar(20) NOT NULL DEFAULT '',
+ `command` text DEFAULT NULL,
+ `remark` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT '',
+ `buildin` tinyint(1) NOT NULL DEFAULT 0,
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `lastTime` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `lastTime` (`lastTime`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_dashboard` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `dimension` int(8) NOT NULL DEFAULT 0,
+ `module` mediumint(8) NOT NULL DEFAULT 0,
+ `desc` mediumtext DEFAULT NULL,
+ `layout` mediumtext DEFAULT NULL,
+ `filters` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_dataset` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(155) NOT NULL DEFAULT '',
+ `sql` text DEFAULT NULL,
+ `fields` mediumtext DEFAULT NULL,
+ `objects` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_dataview` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `group` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(155) NOT NULL DEFAULT '',
+ `code` varchar(50) NOT NULL DEFAULT '',
+ `mode` enum('text','builder') NOT NULL DEFAULT 'builder',
+ `view` varchar(57) NOT NULL DEFAULT '',
+ `sql` text DEFAULT NULL,
+ `fields` mediumtext DEFAULT NULL,
+ `langs` text DEFAULT NULL,
+ `objects` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` tinyint(4) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_demand` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `pool` int(8) NOT NULL DEFAULT 0,
+ `module` int(8) NOT NULL DEFAULT 0,
+ `product` varchar(255) NOT NULL DEFAULT '',
+ `parent` mediumint(8) NOT NULL DEFAULT 0,
+ `pri` char(30) NOT NULL DEFAULT '',
+ `category` char(30) NOT NULL DEFAULT '',
+ `source` char(30) NOT NULL DEFAULT '',
+ `sourceNote` varchar(255) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `feedbackedBy` varchar(255) NOT NULL DEFAULT '',
+ `email` varchar(255) NOT NULL DEFAULT '',
+ `assignedTo` char(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `reviewedBy` text DEFAULT NULL,
+ `reviewedDate` datetime DEFAULT NULL,
+ `status` char(30) NOT NULL DEFAULT '',
+ `stage` enum('wait','distributed','inroadmap','incharter','developing','delivering','delivered','closed') NOT NULL DEFAULT 'wait',
+ `duration` char(30) NOT NULL DEFAULT '',
+ `BSA` char(30) NOT NULL DEFAULT '',
+ `story` mediumint(8) NOT NULL DEFAULT 0,
+ `roadmap` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `mailto` text DEFAULT NULL,
+ `duplicateDemand` mediumint(8) DEFAULT NULL,
+ `childDemands` varchar(255) NOT NULL DEFAULT '',
+ `version` varchar(255) NOT NULL DEFAULT '',
+ `parentVersion` smallint(6) NOT NULL DEFAULT 0,
+ `vision` varchar(255) NOT NULL DEFAULT 'or',
+ `color` varchar(255) NOT NULL DEFAULT '',
+ `changedBy` char(30) NOT NULL DEFAULT '',
+ `changedDate` datetime DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(30) NOT NULL DEFAULT '',
+ `submitedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `activatedDate` datetime DEFAULT NULL,
+ `distributedBy` varchar(30) NOT NULL DEFAULT '',
+ `distributedDate` datetime DEFAULT NULL,
+ `feedback` mediumint(9) NOT NULL DEFAULT 0,
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_demandpool` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `status` char(30) NOT NULL DEFAULT '',
+ `products` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `owner` text DEFAULT NULL,
+ `reviewer` text DEFAULT NULL,
+ `acl` char(30) DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_demandreview` (
+ `demand` mediumint(9) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `reviewer` varchar(30) NOT NULL DEFAULT '',
+ `result` varchar(30) NOT NULL DEFAULT '',
+ `reviewDate` datetime DEFAULT NULL,
+ UNIQUE KEY `demand` (`demand`,`version`,`reviewer`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_demandspec` (
+ `demand` mediumint(9) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `spec` mediumtext DEFAULT NULL,
+ `verify` mediumtext DEFAULT NULL,
+ `files` text DEFAULT NULL,
+ UNIQUE KEY `demand` (`demand`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_deploy` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `begin` datetime DEFAULT NULL,
+ `end` datetime DEFAULT NULL,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `owner` char(30) NOT NULL DEFAULT '',
+ `members` text DEFAULT NULL,
+ `notify` text DEFAULT NULL,
+ `cases` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `result` varchar(20) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_deployproduct` (
+ `deploy` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `release` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `package` varchar(255) NOT NULL DEFAULT '',
+ UNIQUE KEY `deploy_product_release` (`deploy`,`product`,`release`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_deployscope` (
+ `deploy` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `service` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `hosts` text DEFAULT NULL,
+ `remove` text DEFAULT NULL,
+ `add` text DEFAULT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_deploystep` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `deploy` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `begin` datetime DEFAULT NULL,
+ `end` datetime DEFAULT NULL,
+ `stage` varchar(30) NOT NULL DEFAULT '',
+ `content` text DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `assignedTo` char(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `finishedBy` char(30) NOT NULL DEFAULT '',
+ `finishedDate` datetime DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_dept` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` char(60) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `order` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `position` char(30) NOT NULL DEFAULT '',
+ `function` char(255) NOT NULL DEFAULT '',
+ `manager` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ KEY `parent` (`parent`),
+ KEY `path` (`path`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_design` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` varchar(255) NOT NULL DEFAULT '',
+ `product` varchar(255) NOT NULL DEFAULT '',
+ `commit` text DEFAULT NULL,
+ `commitedBy` varchar(30) NOT NULL DEFAULT '',
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `story` char(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_designspec` (
+ `design` mediumint(8) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `files` varchar(255) NOT NULL DEFAULT '',
+ UNIQUE KEY `design` (`design`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_dimension` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(90) NOT NULL DEFAULT '',
+ `code` varchar(45) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `acl` enum('open','private') NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `code` (`code`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_doc` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `lib` varchar(30) NOT NULL DEFAULT '',
+ `template` varchar(30) NOT NULL DEFAULT '',
+ `templateType` varchar(30) NOT NULL DEFAULT '',
+ `chapterType` varchar(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT 'normal',
+ `parent` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `order` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `views` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `assetLib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `assetLibType` varchar(30) NOT NULL DEFAULT '',
+ `from` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromVersion` smallint(6) NOT NULL DEFAULT 1,
+ `draft` longtext DEFAULT NULL,
+ `collects` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `addedBy` varchar(30) NOT NULL DEFAULT '',
+ `addedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `approvedDate` date DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `editingDate` text DEFAULT NULL,
+ `editedList` text DEFAULT NULL,
+ `mailto` text DEFAULT NULL,
+ `acl` varchar(10) NOT NULL DEFAULT 'open',
+ `groups` varchar(255) NOT NULL DEFAULT '',
+ `users` text DEFAULT NULL,
+ `version` smallint(6) unsigned NOT NULL DEFAULT 1,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `execution` (`execution`),
+ KEY `lib` (`lib`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_docaction` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `doc` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `action` varchar(80) NOT NULL DEFAULT '',
+ `actor` char(30) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `doc` (`doc`),
+ KEY `actor` (`actor`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_doccontent` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `doc` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `digest` varchar(255) NOT NULL DEFAULT '',
+ `content` longtext DEFAULT NULL,
+ `files` text DEFAULT NULL,
+ `type` varchar(10) NOT NULL DEFAULT '',
+ `version` smallint(6) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `doc_version` (`doc`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_doclib` (
+ `id` smallint(6) unsigned NOT NULL AUTO_INCREMENT,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(60) NOT NULL DEFAULT '',
+ `baseUrl` varchar(255) NOT NULL DEFAULT '',
+ `acl` varchar(10) NOT NULL DEFAULT 'open',
+ `groups` varchar(255) NOT NULL DEFAULT '',
+ `users` text DEFAULT NULL,
+ `main` enum('0','1') NOT NULL DEFAULT '0',
+ `collector` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `order` tinyint(5) unsigned NOT NULL DEFAULT 0,
+ `addedBy` varchar(30) NOT NULL DEFAULT '',
+ `addedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `execution` (`execution`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_domain` (
+ `id` smallint(5) unsigned NOT NULL AUTO_INCREMENT,
+ `domain` varchar(255) NOT NULL DEFAULT '',
+ `adminURI` varchar(255) NOT NULL DEFAULT '',
+ `resolverURI` varchar(255) NOT NULL DEFAULT '',
+ `register` varchar(255) NOT NULL DEFAULT '',
+ `expiredDate` datetime DEFAULT NULL,
+ `renew` varchar(255) NOT NULL DEFAULT '',
+ `account` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `domain` (`domain`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_duckdbqueue` (
+ `object` varchar(255) NOT NULL DEFAULT '',
+ `updatedTime` datetime DEFAULT NULL,
+ `syncTime` datetime DEFAULT NULL,
+ UNIQUE KEY `object` (`object`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_durationestimation` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `stage` mediumint(9) NOT NULL DEFAULT 0,
+ `workload` varchar(255) NOT NULL DEFAULT '',
+ `worktimeRate` varchar(255) NOT NULL DEFAULT '',
+ `people` varchar(255) NOT NULL DEFAULT '',
+ `startDate` date DEFAULT NULL,
+ `endDate` date DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_effort` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` text DEFAULT NULL,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `work` text DEFAULT NULL,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `date` date DEFAULT NULL,
+ `left` float NOT NULL DEFAULT 0,
+ `consumed` float NOT NULL DEFAULT 0,
+ `begin` smallint(4) unsigned zerofill NOT NULL DEFAULT 0000,
+ `end` smallint(4) unsigned zerofill NOT NULL DEFAULT 0000,
+ `extra` text DEFAULT NULL,
+ `order` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `execution` (`execution`),
+ KEY `objectID` (`objectID`),
+ KEY `date` (`date`),
+ KEY `account` (`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_entry` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `code` varchar(20) NOT NULL DEFAULT '',
+ `key` varchar(32) NOT NULL DEFAULT '',
+ `freePasswd` enum('0','1') NOT NULL DEFAULT '0',
+ `ip` varchar(100) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `calledTime` int(11) unsigned NOT NULL DEFAULT 0,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_expect` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `userID` mediumint(8) NOT NULL DEFAULT 0,
+ `project` mediumint(8) NOT NULL DEFAULT 0,
+ `expect` text DEFAULT NULL,
+ `progress` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_extension` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(150) NOT NULL DEFAULT '',
+ `code` varchar(30) NOT NULL DEFAULT '',
+ `version` varchar(50) NOT NULL DEFAULT '',
+ `author` varchar(100) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `license` text DEFAULT NULL,
+ `type` varchar(20) NOT NULL DEFAULT 'extension',
+ `site` varchar(150) NOT NULL DEFAULT '',
+ `zentaoCompatible` text DEFAULT NULL,
+ `installedTime` datetime DEFAULT NULL,
+ `depends` varchar(100) NOT NULL DEFAULT '',
+ `dirs` mediumtext DEFAULT NULL,
+ `files` mediumtext DEFAULT NULL,
+ `status` varchar(20) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `code` (`code`),
+ KEY `name` (`name`),
+ KEY `installedTime` (`installedTime`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_faq` (
+ `id` mediumint(9) NOT NULL AUTO_INCREMENT,
+ `module` mediumint(9) NOT NULL DEFAULT 0,
+ `product` mediumint(9) NOT NULL DEFAULT 0,
+ `question` varchar(255) NOT NULL DEFAULT '',
+ `answer` text DEFAULT NULL,
+ `addedtime` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_feedback` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `solution` char(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 2,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `public` enum('0','1') NOT NULL DEFAULT '0',
+ `notify` enum('0','1') NOT NULL DEFAULT '0',
+ `notifyEmail` varchar(100) NOT NULL DEFAULT '',
+ `source` varchar(255) NOT NULL DEFAULT '',
+ `likes` text DEFAULT NULL,
+ `result` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `faq` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `openedBy` char(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `reviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `processedBy` char(30) NOT NULL DEFAULT '',
+ `processedDate` datetime DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(30) NOT NULL DEFAULT '',
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(255) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `activatedBy` varchar(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `feedbackBy` varchar(100) NOT NULL DEFAULT '',
+ `repeatFeedback` mediumint(8) NOT NULL DEFAULT 0,
+ `mailto` varchar(255) NOT NULL DEFAULT '',
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_feedbackview` (
+ `account` char(30) NOT NULL DEFAULT '',
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `account_product` (`account`,`product`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_file` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `pathname` char(100) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `extension` char(30) NOT NULL DEFAULT '',
+ `size` int(11) unsigned NOT NULL DEFAULT 0,
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `addedBy` char(30) NOT NULL DEFAULT '',
+ `addedDate` datetime DEFAULT NULL,
+ `downloads` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `extra` varchar(255) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `objectType` (`objectType`),
+ KEY `objectID` (`objectID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_gapanalysis` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `role` varchar(20) NOT NULL DEFAULT '',
+ `analysis` mediumtext DEFAULT NULL,
+ `needTrain` enum('no','yes') NOT NULL DEFAULT 'no',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `project_account` (`project`,`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_group` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `name` char(30) NOT NULL DEFAULT '',
+ `role` char(30) NOT NULL DEFAULT '',
+ `desc` char(255) NOT NULL DEFAULT '',
+ `acl` text DEFAULT NULL,
+ `developer` enum('0','1') NOT NULL DEFAULT '1',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_grouppriv` (
+ `group` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` char(30) NOT NULL DEFAULT '',
+ `method` char(30) NOT NULL DEFAULT '',
+ UNIQUE KEY `group` (`group`,`module`,`method`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_history` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `action` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `field` varchar(30) NOT NULL DEFAULT '',
+ `old` text DEFAULT NULL,
+ `new` text DEFAULT NULL,
+ `diff` mediumtext DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `action` (`action`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_holiday` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(30) NOT NULL DEFAULT '',
+ `type` enum('holiday','working') NOT NULL DEFAULT 'holiday',
+ `desc` text DEFAULT NULL,
+ `year` char(4) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `year` (`year`),
+ KEY `name` (`name`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_host` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT 'normal',
+ `hostType` varchar(30) NOT NULL DEFAULT '',
+ `mac` varchar(128) NOT NULL DEFAULT '',
+ `memory` varchar(30) NOT NULL DEFAULT '',
+ `diskSize` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(50) NOT NULL DEFAULT '',
+ `secret` varchar(50) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `tokenSN` varchar(50) NOT NULL DEFAULT '',
+ `tokenTime` datetime DEFAULT NULL,
+ `oldTokenSN` varchar(50) NOT NULL DEFAULT '',
+ `vsoft` varchar(30) NOT NULL DEFAULT '',
+ `heartbeat` datetime DEFAULT NULL,
+ `zap` varchar(10) NOT NULL DEFAULT '',
+ `provider` varchar(255) NOT NULL DEFAULT '',
+ `vnc` int(11) NOT NULL DEFAULT 0,
+ `ztf` int(11) NOT NULL DEFAULT 0,
+ `zd` int(11) NOT NULL DEFAULT 0,
+ `ssh` int(11) NOT NULL DEFAULT 0,
+ `parent` int(11) unsigned NOT NULL DEFAULT 0,
+ `image` int(11) unsigned NOT NULL DEFAULT 0,
+ `admin` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `serverRoom` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `serverModel` varchar(256) NOT NULL DEFAULT '',
+ `hardwareType` varchar(64) NOT NULL DEFAULT '',
+ `cpuBrand` varchar(128) NOT NULL DEFAULT '',
+ `cpuModel` varchar(128) NOT NULL DEFAULT '',
+ `cpuNumber` varchar(16) NOT NULL DEFAULT '',
+ `cpuCores` varchar(30) NOT NULL DEFAULT '',
+ `intranet` varchar(128) NOT NULL DEFAULT '',
+ `extranet` varchar(128) NOT NULL DEFAULT '',
+ `osName` varchar(64) NOT NULL DEFAULT '',
+ `osVersion` varchar(64) NOT NULL DEFAULT '',
+ `group` varchar(128) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_chat` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `gid` char(40) NOT NULL DEFAULT '',
+ `name` varchar(60) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT 'group',
+ `admins` varchar(255) NOT NULL DEFAULT '',
+ `committers` varchar(255) NOT NULL DEFAULT '',
+ `subject` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `public` enum('0','1') NOT NULL DEFAULT '0',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `ownedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `mergedDate` datetime DEFAULT NULL,
+ `lastActiveTime` datetime DEFAULT NULL,
+ `lastMessage` int(11) unsigned NOT NULL DEFAULT 0,
+ `lastMessageIndex` int(11) unsigned NOT NULL DEFAULT 0,
+ `dismissDate` datetime DEFAULT NULL,
+ `pinnedMessages` text DEFAULT NULL,
+ `mergedChats` text DEFAULT NULL,
+ `adminInvite` enum('0','1') NOT NULL DEFAULT '0',
+ `avatar` text DEFAULT NULL,
+ `archiveDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `gid` (`gid`),
+ KEY `name` (`name`),
+ KEY `type` (`type`),
+ KEY `public` (`public`),
+ KEY `createdBy` (`createdBy`),
+ KEY `editedBy` (`editedBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_chat_message_index` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `gid` char(40) NOT NULL,
+ `tableName` char(64) NOT NULL,
+ `start` int(11) unsigned NOT NULL,
+ `end` int(11) unsigned NOT NULL,
+ `startIndex` int(11) unsigned NOT NULL,
+ `endIndex` int(11) unsigned NOT NULL,
+ `startDate` datetime DEFAULT NULL,
+ `endDate` datetime DEFAULT NULL,
+ `count` mediumint(8) unsigned NOT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `chattable` (`gid`,`tableName`),
+ KEY `start` (`start`),
+ KEY `end` (`end`),
+ KEY `startDate` (`startDate`),
+ KEY `endDate` (`endDate`),
+ KEY `chatstartindex` (`gid`,`startIndex`),
+ KEY `chatendindex` (`gid`,`endIndex`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_chatuser` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `cgid` char(40) NOT NULL DEFAULT '',
+ `user` mediumint(8) NOT NULL DEFAULT 0,
+ `order` smallint(5) NOT NULL DEFAULT 0,
+ `star` enum('0','1') NOT NULL DEFAULT '0',
+ `hide` enum('0','1') NOT NULL DEFAULT '0',
+ `mute` enum('0','1') NOT NULL DEFAULT '0',
+ `freeze` enum('0','1') NOT NULL DEFAULT '0',
+ `join` datetime DEFAULT NULL,
+ `quit` datetime DEFAULT NULL,
+ `category` varchar(40) NOT NULL DEFAULT '',
+ `lastReadMessage` int(11) unsigned NOT NULL DEFAULT 0,
+ `lastReadMessageIndex` int(11) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `chatuser` (`cgid`,`user`),
+ KEY `cgid` (`cgid`),
+ KEY `user` (`user`),
+ KEY `order` (`order`),
+ KEY `star` (`star`),
+ KEY `hide` (`hide`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_client` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `version` char(30) NOT NULL DEFAULT '',
+ `desc` varchar(100) NOT NULL DEFAULT '',
+ `changeLog` text DEFAULT NULL,
+ `strategy` varchar(10) NOT NULL DEFAULT '',
+ `downloads` text DEFAULT NULL,
+ `createdDate` datetime DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `status` enum('released','wait') NOT NULL DEFAULT 'wait',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_conference` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `rid` char(40) NOT NULL DEFAULT '',
+ `cgid` char(40) NOT NULL DEFAULT '',
+ `status` enum('closed','open','notStarted','canceled') NOT NULL DEFAULT 'closed',
+ `participants` text DEFAULT NULL,
+ `subscribers` text DEFAULT NULL,
+ `invitee` text DEFAULT NULL,
+ `openedBy` mediumint(8) NOT NULL DEFAULT 0,
+ `openedDate` datetime DEFAULT NULL,
+ `topic` text DEFAULT NULL,
+ `startTime` datetime DEFAULT NULL,
+ `endTime` datetime DEFAULT NULL,
+ `password` char(20) NOT NULL DEFAULT '',
+ `type` enum('default','periodic','scheduled') NOT NULL DEFAULT 'default',
+ `number` char(20) NOT NULL DEFAULT '',
+ `note` text DEFAULT NULL,
+ `sentNotify` tinyint(1) NOT NULL DEFAULT 0,
+ `reminderTime` int(11) NOT NULL DEFAULT 0,
+ `moderators` text DEFAULT NULL,
+ `isPrivate` enum('0','1') NOT NULL DEFAULT '0',
+ `isInner` enum('0','1') NOT NULL DEFAULT '1',
+ PRIMARY KEY (`id`),
+ KEY `status` (`status`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_conferenceaction` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `rid` char(40) NOT NULL DEFAULT '',
+ `type` enum('create','invite','join','leave','close','publish') NOT NULL DEFAULT 'create',
+ `data` text DEFAULT NULL,
+ `user` mediumint(8) NOT NULL DEFAULT 0,
+ `date` datetime DEFAULT NULL,
+ `device` char(40) NOT NULL DEFAULT 'default',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_conferenceinvite` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `conferenceID` mediumint(8) unsigned NOT NULL,
+ `inviteeID` mediumint(8) unsigned NOT NULL,
+ `status` enum('pending','accepted','rejected') NOT NULL DEFAULT 'pending',
+ `createdDate` datetime DEFAULT NULL,
+ `updatedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `conference_user` (`conferenceID`,`inviteeID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_conferenceuser` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `conference` mediumint(8) NOT NULL DEFAULT 0,
+ `user` mediumint(8) NOT NULL DEFAULT 0,
+ `hide` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `conferenceuser` (`conference`,`user`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_message` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `gid` char(40) NOT NULL DEFAULT '',
+ `cgid` char(40) NOT NULL DEFAULT '',
+ `user` varchar(30) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `index` int(11) unsigned NOT NULL DEFAULT 0,
+ `type` enum('normal','broadcast','notify','bulletin','botcommand') NOT NULL DEFAULT 'normal',
+ `content` text DEFAULT NULL,
+ `contentType` enum('text','plain','emotion','image','file','object','code') NOT NULL DEFAULT 'text',
+ `data` text DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `legacy` tinyint(1) NOT NULL DEFAULT 0,
+ `uniqueIndex` int(11) GENERATED ALWAYS AS (case when `legacy` = 1 then NULL when `cgid` = 'notification' then NULL else `index` end) STORED,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `uniqueIndexInChat` (`cgid`,`uniqueIndex`),
+ KEY `mgid` (`gid`),
+ KEY `mcgid` (`cgid`),
+ KEY `muser` (`user`),
+ KEY `mtype` (`type`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_message_backup` (
+ `id` int(11) unsigned NOT NULL,
+ `gid` char(40) NOT NULL DEFAULT '',
+ `cgid` char(40) NOT NULL DEFAULT '',
+ `user` varchar(30) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `index` int(11) unsigned NOT NULL DEFAULT 0,
+ `type` enum('normal','broadcast','notify') NOT NULL DEFAULT 'normal',
+ `content` text DEFAULT NULL,
+ `contentType` enum('text','plain','emotion','image','file','object','code') NOT NULL DEFAULT 'text',
+ `data` text DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0'
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_message_index` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `tableName` char(64) NOT NULL,
+ `start` int(11) unsigned NOT NULL,
+ `end` int(11) unsigned NOT NULL,
+ `startDate` datetime DEFAULT NULL,
+ `endDate` datetime DEFAULT NULL,
+ `chats` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `tableName` (`tableName`),
+ KEY `start` (`start`),
+ KEY `end` (`end`),
+ KEY `startDate` (`startDate`),
+ KEY `endDate` (`endDate`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_messagestatus` (
+ `user` mediumint(8) NOT NULL DEFAULT 0,
+ `message` int(11) unsigned NOT NULL,
+ `status` enum('waiting','sent','readed','deleted') NOT NULL DEFAULT 'waiting',
+ UNIQUE KEY `user` (`user`,`message`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_queue` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` char(30) NOT NULL,
+ `content` text DEFAULT NULL,
+ `addDate` datetime DEFAULT NULL,
+ `processDate` datetime DEFAULT NULL,
+ `result` text DEFAULT NULL,
+ `status` char(30) NOT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_im_userdevice` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `user` mediumint(8) NOT NULL DEFAULT 0,
+ `device` char(40) NOT NULL DEFAULT 'default',
+ `deviceID` char(40) NOT NULL DEFAULT '',
+ `token` char(64) NOT NULL DEFAULT '',
+ `validUntil` datetime DEFAULT NULL,
+ `lastLogin` datetime DEFAULT NULL,
+ `lastLogout` datetime DEFAULT NULL,
+ `online` tinyint(1) NOT NULL DEFAULT 0,
+ `version` char(10) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `userdevice` (`user`,`device`),
+ KEY `user` (`user`),
+ KEY `lastLogin` (`lastLogin`),
+ KEY `lastLogout` (`lastLogout`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_image` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `host` int(11) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(64) NOT NULL DEFAULT '',
+ `localName` varchar(64) NOT NULL DEFAULT '',
+ `address` varchar(64) NOT NULL DEFAULT '',
+ `path` varchar(64) NOT NULL DEFAULT '',
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `osName` varchar(32) NOT NULL DEFAULT '',
+ `from` varchar(10) NOT NULL DEFAULT 'zentao',
+ `memory` float unsigned NOT NULL DEFAULT 0,
+ `disk` float unsigned NOT NULL DEFAULT 0,
+ `fileSize` float unsigned NOT NULL DEFAULT 0,
+ `md5` varchar(64) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `restoreDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_instance` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `space` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `solution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` char(50) NOT NULL DEFAULT '',
+ `appID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `appName` char(50) NOT NULL DEFAULT '',
+ `appVersion` char(20) NOT NULL DEFAULT '',
+ `chart` char(50) NOT NULL DEFAULT '',
+ `logo` varchar(255) NOT NULL DEFAULT '',
+ `version` char(50) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `introduction` text DEFAULT NULL,
+ `source` char(20) NOT NULL DEFAULT '',
+ `channel` char(20) NOT NULL DEFAULT '',
+ `k8name` char(64) NOT NULL DEFAULT '',
+ `status` char(20) NOT NULL DEFAULT '',
+ `pinned` enum('0','1') NOT NULL DEFAULT '0',
+ `domain` char(255) NOT NULL DEFAULT '',
+ `smtpSnippetName` char(30) NOT NULL DEFAULT '',
+ `ldapSnippetName` char(30) NOT NULL DEFAULT '',
+ `ldapSettings` text DEFAULT NULL,
+ `dbSettings` text DEFAULT NULL,
+ `autoBackup` tinyint(1) NOT NULL DEFAULT 0,
+ `backupKeepDays` int(10) unsigned NOT NULL DEFAULT 1,
+ `autoRestore` tinyint(1) NOT NULL DEFAULT 0,
+ `env` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdAt` datetime DEFAULT NULL,
+ `deleted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `space` (`space`),
+ KEY `k8name` (`k8name`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_intervention` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `activity` mediumint(8) NOT NULL DEFAULT 0,
+ `status` char(30) NOT NULL DEFAULT '',
+ `partake` text DEFAULT NULL,
+ `begin` date DEFAULT NULL,
+ `realBegin` date DEFAULT NULL,
+ `situation` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `project` (`project`,`activity`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_issue` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `project` varchar(255) NOT NULL DEFAULT '',
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `pri` char(30) NOT NULL DEFAULT '',
+ `severity` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `activity` varchar(255) NOT NULL DEFAULT '',
+ `deadline` date DEFAULT NULL,
+ `resolution` char(30) NOT NULL DEFAULT '',
+ `resolutionComment` text DEFAULT NULL,
+ `objectID` varchar(255) NOT NULL DEFAULT '',
+ `resolvedDate` date DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `owner` varchar(255) NOT NULL DEFAULT '',
+ `lib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `from` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `activateBy` varchar(30) NOT NULL DEFAULT '',
+ `activateDate` date DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` date DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `approvedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_job` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `repo` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `frame` varchar(20) NOT NULL DEFAULT '',
+ `engine` varchar(20) NOT NULL DEFAULT '',
+ `server` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `pipeline` varchar(500) NOT NULL DEFAULT '',
+ `triggerType` varchar(255) NOT NULL DEFAULT '',
+ `sonarqubeServer` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `projectKey` varchar(255) NOT NULL DEFAULT '',
+ `svnDir` varchar(255) NOT NULL DEFAULT '',
+ `atDay` varchar(255) NOT NULL DEFAULT '',
+ `atTime` varchar(10) NOT NULL DEFAULT '',
+ `customParam` text DEFAULT NULL,
+ `comment` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `lastExec` datetime DEFAULT NULL,
+ `lastStatus` varchar(255) NOT NULL DEFAULT '',
+ `lastTag` varchar(255) NOT NULL DEFAULT '',
+ `lastSyncDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `idx_repo_deleted` (`repo`,`deleted`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanban` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `space` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `team` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `acl` char(30) NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `archived` enum('0','1') NOT NULL DEFAULT '1',
+ `performable` enum('0','1') NOT NULL DEFAULT '0',
+ `status` enum('active','closed') NOT NULL DEFAULT 'active',
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `displayCards` smallint(6) NOT NULL DEFAULT 0,
+ `showWIP` enum('0','1') NOT NULL DEFAULT '1',
+ `fluidBoard` enum('0','1') NOT NULL DEFAULT '0',
+ `colWidth` smallint(4) NOT NULL DEFAULT 264,
+ `minColWidth` smallint(4) NOT NULL DEFAULT 200,
+ `maxColWidth` smallint(4) NOT NULL DEFAULT 384,
+ `object` varchar(255) NOT NULL DEFAULT '',
+ `alignment` varchar(10) NOT NULL DEFAULT 'center',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `activatedBy` char(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbancard` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `kanban` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `region` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `group` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromType` varchar(30) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT 'doing',
+ `pri` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `assignedTo` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `estimate` float unsigned NOT NULL DEFAULT 0,
+ `progress` float unsigned NOT NULL DEFAULT 0,
+ `color` char(7) NOT NULL DEFAULT '',
+ `acl` char(30) NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `archived` enum('0','1') NOT NULL DEFAULT '0',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `archivedBy` char(30) NOT NULL DEFAULT '',
+ `archivedDate` datetime DEFAULT NULL,
+ `assignedBy` char(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbancell` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `kanban` mediumint(8) NOT NULL DEFAULT 0,
+ `lane` mediumint(8) NOT NULL DEFAULT 0,
+ `column` mediumint(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ `cards` mediumtext DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `card_group` (`kanban`,`type`,`lane`,`column`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbancolumn` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `parent` mediumint(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ `region` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `group` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `color` char(30) NOT NULL DEFAULT '',
+ `limit` smallint(6) NOT NULL DEFAULT -1,
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `archived` enum('0','1') NOT NULL DEFAULT '0',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbangroup` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `kanban` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `region` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `order` smallint(6) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbanlane` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `execution` mediumint(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ `region` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `group` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `groupby` char(30) NOT NULL DEFAULT '',
+ `extra` char(30) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `color` char(30) NOT NULL DEFAULT '',
+ `order` smallint(6) NOT NULL DEFAULT 0,
+ `lastEditedTime` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbanregion` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `space` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `kanban` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_kanbanspace` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(50) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `team` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `acl` char(30) NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `status` enum('active','closed') NOT NULL DEFAULT 'active',
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `activatedBy` char(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_lang` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `lang` varchar(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `section` varchar(50) NOT NULL DEFAULT '',
+ `key` varchar(60) NOT NULL DEFAULT '',
+ `value` text DEFAULT NULL,
+ `system` enum('0','1') NOT NULL DEFAULT '1',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `lang` (`lang`,`module`,`section`,`key`,`vision`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_leave` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `year` char(4) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `start` time DEFAULT NULL,
+ `finish` time DEFAULT NULL,
+ `hours` float(4,1) unsigned NOT NULL DEFAULT 0.0,
+ `backDate` datetime DEFAULT NULL,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `reviewedBy` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `level` tinyint(3) NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `reviewers` text DEFAULT NULL,
+ `backReviewers` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `year` (`year`),
+ KEY `type` (`type`),
+ KEY `status` (`status`),
+ KEY `createdBy` (`createdBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_lieu` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `year` char(4) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `start` time DEFAULT NULL,
+ `finish` time DEFAULT NULL,
+ `hours` float(4,1) unsigned NOT NULL DEFAULT 0.0,
+ `overtime` char(255) NOT NULL DEFAULT '',
+ `trip` char(255) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `reviewedBy` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `level` tinyint(3) NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `reviewers` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `year` (`year`),
+ KEY `status` (`status`),
+ KEY `createdBy` (`createdBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_log` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `action` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `date` datetime DEFAULT NULL,
+ `url` varchar(255) NOT NULL DEFAULT '',
+ `contentType` varchar(30) NOT NULL DEFAULT '',
+ `data` text DEFAULT NULL,
+ `result` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `objectType` (`objectType`),
+ KEY `obejctID` (`objectID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_market` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `industry` char(255) NOT NULL DEFAULT '',
+ `scale` decimal(10,2) NOT NULL DEFAULT 0.00,
+ `maturity` char(255) NOT NULL DEFAULT '',
+ `speed` varchar(255) NOT NULL DEFAULT '',
+ `competition` char(255) NOT NULL DEFAULT '',
+ `strategy` varchar(255) NOT NULL DEFAULT '',
+ `ppm` varchar(20) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_marketreport` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `market` mediumint(8) NOT NULL DEFAULT 0,
+ `research` mediumint(8) NOT NULL DEFAULT 0,
+ `maturity` varchar(30) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `participants` char(255) NOT NULL DEFAULT '',
+ `source` varchar(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `publishedBy` varchar(30) NOT NULL DEFAULT '',
+ `publishedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_measqueue` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `mid` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `status` varchar(255) NOT NULL DEFAULT '',
+ `logs` text DEFAULT NULL,
+ `execTime` varchar(10) NOT NULL DEFAULT '',
+ `params` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `updateDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_measrecords` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `mid` mediumint(8) NOT NULL DEFAULT 0,
+ `measCode` char(50) NOT NULL DEFAULT '',
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `params` text DEFAULT NULL,
+ `year` char(4) NOT NULL DEFAULT '',
+ `month` char(6) NOT NULL DEFAULT '',
+ `week` char(8) NOT NULL DEFAULT '',
+ `day` char(8) NOT NULL DEFAULT '',
+ `value` varchar(255) NOT NULL DEFAULT '',
+ `date` date DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `time` (`year`,`month`,`day`,`week`),
+ KEY `product` (`product`),
+ KEY `project` (`project`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_meastemplate` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `model` char(30) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `content` mediumtext DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_meeting` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) NOT NULL DEFAULT 0,
+ `execution` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `begin` time DEFAULT NULL,
+ `end` time DEFAULT NULL,
+ `dept` mediumint(8) NOT NULL DEFAULT 0,
+ `mode` varchar(255) NOT NULL DEFAULT '',
+ `host` varchar(30) NOT NULL DEFAULT '',
+ `participant` text DEFAULT NULL,
+ `date` date DEFAULT NULL,
+ `room` int(11) NOT NULL DEFAULT 0,
+ `minutes` text DEFAULT NULL,
+ `minutedBy` varchar(30) NOT NULL DEFAULT '',
+ `minutedDate` datetime DEFAULT NULL,
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_meetingroom` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `position` varchar(30) NOT NULL DEFAULT '',
+ `seats` int(11) NOT NULL DEFAULT 0,
+ `equipment` varchar(255) NOT NULL DEFAULT '',
+ `openTime` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_metric` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `purpose` varchar(50) NOT NULL DEFAULT '',
+ `scope` char(30) NOT NULL DEFAULT '',
+ `object` char(30) NOT NULL DEFAULT '',
+ `stage` enum('wait','released') DEFAULT 'wait',
+ `type` enum('php','sql') DEFAULT 'php',
+ `name` varchar(90) NOT NULL DEFAULT '',
+ `alias` varchar(90) NOT NULL DEFAULT '',
+ `code` varchar(90) NOT NULL DEFAULT '',
+ `unit` varchar(10) NOT NULL DEFAULT '',
+ `dateType` varchar(50) NOT NULL DEFAULT '',
+ `collector` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `definition` text DEFAULT NULL,
+ `when` varchar(30) NOT NULL DEFAULT '',
+ `event` varchar(30) NOT NULL DEFAULT '',
+ `cronCFG` varchar(30) NOT NULL DEFAULT '',
+ `time` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `implementedBy` varchar(30) NOT NULL DEFAULT '',
+ `implementedDate` datetime DEFAULT NULL,
+ `delistedBy` varchar(30) NOT NULL DEFAULT '',
+ `delistedDate` datetime DEFAULT NULL,
+ `builtin` enum('0','1') NOT NULL DEFAULT '0',
+ `fromID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `order` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `lastCalcRows` int(11) NOT NULL DEFAULT 0,
+ `lastCalcTime` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_metriclib` (
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
+ `metricID` mediumint(9) NOT NULL DEFAULT 0,
+ `metricCode` varchar(100) NOT NULL DEFAULT '',
+ `system` char(30) NOT NULL DEFAULT '0',
+ `program` char(30) NOT NULL DEFAULT '',
+ `project` char(30) NOT NULL DEFAULT '',
+ `product` char(30) NOT NULL DEFAULT '',
+ `execution` char(30) NOT NULL DEFAULT '',
+ `code` char(30) NOT NULL DEFAULT '',
+ `pipeline` char(30) NOT NULL DEFAULT '',
+ `repo` char(30) NOT NULL DEFAULT '',
+ `user` text DEFAULT NULL,
+ `dept` char(30) NOT NULL DEFAULT '',
+ `year` char(4) NOT NULL DEFAULT '0',
+ `month` char(2) NOT NULL DEFAULT '0',
+ `week` char(2) NOT NULL DEFAULT '0',
+ `day` char(2) NOT NULL DEFAULT '0',
+ `value` varchar(100) NOT NULL DEFAULT '0',
+ `calcType` enum('cron','inference') NOT NULL DEFAULT 'cron',
+ `calculatedBy` varchar(30) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `metricID` (`metricID`),
+ KEY `metricCode` (`metricCode`),
+ KEY `date` (`date`),
+ KEY `deleted` (`deleted`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_module` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `root` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` char(60) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT '',
+ `from` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `collector` text DEFAULT NULL,
+ `short` varchar(30) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `root` (`root`),
+ KEY `type` (`type`),
+ KEY `path` (`path`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_mr` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `hostID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `sourceProject` varchar(50) NOT NULL DEFAULT '',
+ `sourceBranch` varchar(100) NOT NULL DEFAULT '',
+ `targetProject` varchar(50) NOT NULL DEFAULT '',
+ `targetBranch` varchar(100) NOT NULL DEFAULT '',
+ `mriid` int(10) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `description` text DEFAULT NULL,
+ `assignee` varchar(255) NOT NULL DEFAULT '',
+ `reviewer` varchar(255) NOT NULL DEFAULT '',
+ `approver` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `status` char(30) NOT NULL DEFAULT '',
+ `mergeStatus` char(30) NOT NULL DEFAULT '',
+ `approvalStatus` char(30) NOT NULL DEFAULT '',
+ `needApproved` enum('0','1') NOT NULL DEFAULT '0',
+ `needCI` enum('0','1') NOT NULL DEFAULT '0',
+ `repoID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `jobID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `executionID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `compileID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `compileStatus` char(30) NOT NULL DEFAULT '',
+ `removeSourceBranch` enum('0','1') NOT NULL DEFAULT '0',
+ `squash` enum('0','1') NOT NULL DEFAULT '0',
+ `isFlow` enum('0','1') NOT NULL DEFAULT '0',
+ `synced` enum('0','1') NOT NULL DEFAULT '1',
+ `syncError` varchar(255) NOT NULL DEFAULT '',
+ `hasNoConflict` enum('0','1') NOT NULL DEFAULT '0',
+ `diffs` longtext DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_mrapproval` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `mrID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` varchar(255) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `action` char(30) NOT NULL DEFAULT '',
+ `comment` text DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_nc` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `auditplan` mediumint(8) NOT NULL DEFAULT 0,
+ `listID` mediumint(8) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `type` char(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT 'active',
+ `severity` char(30) NOT NULL DEFAULT '',
+ `deadline` date DEFAULT NULL,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `resolution` char(30) NOT NULL DEFAULT '',
+ `resolvedDate` date DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` date DEFAULT NULL,
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` date DEFAULT NULL,
+ `activateDate` date DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_notify` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `objectType` varchar(50) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `action` mediumint(8) NOT NULL DEFAULT 0,
+ `toList` text DEFAULT NULL,
+ `ccList` text DEFAULT NULL,
+ `subject` text DEFAULT NULL,
+ `data` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `sendTime` datetime DEFAULT NULL,
+ `status` varchar(10) NOT NULL DEFAULT 'wait',
+ `failReason` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `objectType` (`objectType`),
+ KEY `status` (`status`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_oauth` (
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `openID` varchar(255) NOT NULL DEFAULT '',
+ `providerType` varchar(30) NOT NULL DEFAULT '',
+ `providerID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `account_openID` (`account`,`openID`,`providerType`,`providerID`),
+ KEY `account` (`account`),
+ KEY `providerType` (`providerType`),
+ KEY `providerID` (`providerID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_object` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) NOT NULL DEFAULT 0,
+ `from` mediumint(8) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `category` char(30) NOT NULL DEFAULT '',
+ `version` varchar(255) NOT NULL DEFAULT '',
+ `type` enum('reviewed','taged') NOT NULL DEFAULT 'reviewed',
+ `enabled` enum('0','1') NOT NULL DEFAULT '1',
+ `range` text DEFAULT NULL,
+ `data` text DEFAULT NULL,
+ `storyEst` char(30) NOT NULL DEFAULT '',
+ `taskEst` char(30) NOT NULL DEFAULT '',
+ `requestEst` char(30) NOT NULL DEFAULT '',
+ `testEst` char(30) NOT NULL DEFAULT '',
+ `devEst` char(30) NOT NULL DEFAULT '',
+ `designEst` char(30) NOT NULL DEFAULT '',
+ `end` date DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_opportunity` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `source` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `strategy` char(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT 'active',
+ `impact` mediumint(8) NOT NULL DEFAULT 0,
+ `chance` mediumint(8) NOT NULL DEFAULT 0,
+ `ratio` mediumint(8) NOT NULL DEFAULT 0,
+ `pri` char(30) NOT NULL DEFAULT '',
+ `identifiedDate` date DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` date DEFAULT NULL,
+ `approvedDate` date DEFAULT NULL,
+ `prevention` mediumtext DEFAULT NULL,
+ `plannedClosedDate` date DEFAULT NULL,
+ `actualClosedDate` date DEFAULT NULL,
+ `lib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `from` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `activatedBy` varchar(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `canceledBy` varchar(30) NOT NULL DEFAULT '',
+ `canceledDate` datetime DEFAULT NULL,
+ `cancelReason` char(30) NOT NULL DEFAULT '',
+ `hangupedBy` varchar(30) NOT NULL DEFAULT '',
+ `hangupedDate` datetime DEFAULT NULL,
+ `resolution` mediumtext DEFAULT NULL,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `resolvedDate` datetime DEFAULT NULL,
+ `lastCheckedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastCheckedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_overtime` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `year` char(4) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `start` time DEFAULT NULL,
+ `finish` time DEFAULT NULL,
+ `hours` float(4,1) unsigned NOT NULL DEFAULT 0.0,
+ `leave` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `rejectReason` varchar(100) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `reviewedBy` char(30) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `level` tinyint(3) NOT NULL DEFAULT 0,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `reviewers` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `year` (`year`),
+ KEY `type` (`type`),
+ KEY `status` (`status`),
+ KEY `createdBy` (`createdBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_pipeline` (
+ `id` smallint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` char(30) NOT NULL DEFAULT '',
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `url` varchar(255) DEFAULT NULL,
+ `account` varchar(30) DEFAULT NULL,
+ `password` varchar(255) DEFAULT NULL,
+ `token` varchar(255) DEFAULT NULL,
+ `private` char(32) DEFAULT NULL,
+ `instanceID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_pivot` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `dimension` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `group` varchar(255) NOT NULL DEFAULT '',
+ `code` varchar(255) NOT NULL DEFAULT '',
+ `driver` enum('mysql','duckdb') NOT NULL DEFAULT 'mysql',
+ `mode` enum('text','builder') NOT NULL DEFAULT 'builder',
+ `name` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `acl` enum('open','private') NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `sql` mediumtext DEFAULT NULL,
+ `fields` mediumtext DEFAULT NULL,
+ `langs` mediumtext DEFAULT NULL,
+ `vars` mediumtext DEFAULT NULL,
+ `objects` mediumtext DEFAULT NULL,
+ `settings` mediumtext DEFAULT NULL,
+ `filters` mediumtext DEFAULT NULL,
+ `step` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `stage` enum('draft','published') NOT NULL DEFAULT 'draft',
+ `builtin` enum('0','1') NOT NULL DEFAULT '0',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `dimension` (`dimension`),
+ KEY `group` (`group`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_pivotdrill` (
+ `pivot` mediumint(9) NOT NULL,
+ `field` varchar(255) NOT NULL,
+ `object` varchar(40) NOT NULL,
+ `whereSql` mediumtext NOT NULL,
+ `condition` mediumtext NOT NULL,
+ `status` enum('design','published') NOT NULL DEFAULT 'published',
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `type` enum('auto','manual') NOT NULL DEFAULT 'manual'
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_planstory` (
+ `plan` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `order` mediumint(9) NOT NULL DEFAULT 0,
+ UNIQUE KEY `plan_story` (`plan`,`story`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_practice` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `code` char(50) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `labels` varchar(255) NOT NULL DEFAULT '',
+ `summary` varchar(255) NOT NULL DEFAULT '',
+ `content` text DEFAULT NULL,
+ `contributor` varchar(255) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `code` (`code`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_priv` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `method` varchar(30) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `edition` varchar(30) NOT NULL DEFAULT ',open,biz,max,',
+ `vision` varchar(30) NOT NULL DEFAULT ',rnd,',
+ `system` enum('0','1') NOT NULL DEFAULT '0',
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `priv` (`module`,`method`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_privlang` (
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `objectType` enum('priv','manager') NOT NULL DEFAULT 'priv',
+ `lang` varchar(30) NOT NULL DEFAULT '',
+ `key` varchar(100) NOT NULL DEFAULT '',
+ `value` varchar(255) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ UNIQUE KEY `objectlang` (`objectID`,`objectType`,`lang`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_privmanager` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `code` varchar(100) NOT NULL DEFAULT '',
+ `type` enum('view','module','package') NOT NULL DEFAULT 'package',
+ `edition` varchar(30) NOT NULL DEFAULT ',open,biz,max,',
+ `vision` varchar(30) NOT NULL DEFAULT ',rnd,',
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_privrelation` (
+ `priv` varchar(100) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `relationPriv` varchar(100) NOT NULL DEFAULT '',
+ UNIQUE KEY `privrelation` (`priv`,`type`,`relationPriv`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_process` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `model` char(30) NOT NULL DEFAULT 'waterfall',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `abbr` char(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `order` mediumint(9) NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_product` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `program` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(110) NOT NULL DEFAULT '',
+ `code` varchar(45) NOT NULL DEFAULT '',
+ `shadow` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `bind` enum('0','1') NOT NULL DEFAULT '0',
+ `line` mediumint(8) NOT NULL DEFAULT 0,
+ `type` varchar(30) NOT NULL DEFAULT 'normal',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `PO` varchar(30) NOT NULL DEFAULT '',
+ `QD` varchar(30) NOT NULL DEFAULT '',
+ `RD` varchar(30) NOT NULL DEFAULT '',
+ `feedback` varchar(30) NOT NULL DEFAULT '',
+ `ticket` varchar(30) NOT NULL DEFAULT '',
+ `acl` enum('open','private','custom') NOT NULL DEFAULT 'open',
+ `groups` text DEFAULT NULL,
+ `whitelist` text DEFAULT NULL,
+ `reviewer` text DEFAULT NULL,
+ `PMT` text DEFAULT NULL,
+ `draftEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `activeEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `changingEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `reviewingEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `finishedEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `closedEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `totalEpics` mediumint(8) NOT NULL DEFAULT 0,
+ `draftRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `activeRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `changingRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `reviewingRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `finishedRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `closedRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `totalRequirements` mediumint(8) NOT NULL DEFAULT 0,
+ `draftStories` mediumint(8) NOT NULL DEFAULT 0,
+ `activeStories` mediumint(8) NOT NULL DEFAULT 0,
+ `changingStories` mediumint(8) NOT NULL DEFAULT 0,
+ `reviewingStories` mediumint(8) NOT NULL DEFAULT 0,
+ `finishedStories` mediumint(8) NOT NULL DEFAULT 0,
+ `closedStories` mediumint(8) NOT NULL DEFAULT 0,
+ `totalStories` mediumint(8) NOT NULL DEFAULT 0,
+ `unresolvedBugs` mediumint(8) NOT NULL DEFAULT 0,
+ `closedBugs` mediumint(8) NOT NULL DEFAULT 0,
+ `fixedBugs` mediumint(8) NOT NULL DEFAULT 0,
+ `totalBugs` mediumint(8) NOT NULL DEFAULT 0,
+ `plans` mediumint(8) NOT NULL DEFAULT 0,
+ `releases` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `createdVersion` varchar(20) NOT NULL DEFAULT '',
+ `closedDate` date DEFAULT NULL,
+ `order` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `acl` (`acl`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_productplan` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` varchar(255) NOT NULL DEFAULT '0',
+ `parent` mediumint(9) NOT NULL DEFAULT 0,
+ `title` varchar(90) NOT NULL DEFAULT '',
+ `status` enum('wait','doing','done','closed') NOT NULL DEFAULT 'wait',
+ `desc` mediumtext DEFAULT NULL,
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `finishedDate` datetime DEFAULT NULL,
+ `closedDate` datetime DEFAULT NULL,
+ `order` text DEFAULT NULL,
+ `closedReason` varchar(20) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `end` (`end`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_programactivity` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `process` mediumint(8) NOT NULL DEFAULT 0,
+ `activity` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `content` text DEFAULT NULL,
+ `reason` varchar(255) NOT NULL DEFAULT '',
+ `result` char(30) NOT NULL DEFAULT '',
+ `linkedBy` char(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_programoutput` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `process` mediumint(8) NOT NULL DEFAULT 0,
+ `activity` mediumint(8) NOT NULL DEFAULT 0,
+ `output` mediumint(8) NOT NULL DEFAULT 0,
+ `content` text DEFAULT NULL,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `reason` varchar(255) NOT NULL DEFAULT '',
+ `result` char(30) NOT NULL DEFAULT '',
+ `linkedBy` char(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_programprocess` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `process` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `abbr` char(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `reason` varchar(255) NOT NULL DEFAULT '',
+ `linkedBy` char(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_programreport` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `template` mediumint(8) NOT NULL DEFAULT 0,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `params` text DEFAULT NULL,
+ `content` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_project` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) NOT NULL DEFAULT 0,
+ `charter` mediumint(8) NOT NULL DEFAULT 0,
+ `model` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT 'sprint',
+ `category` char(30) NOT NULL DEFAULT '',
+ `lifetime` char(30) NOT NULL DEFAULT '',
+ `budget` varchar(30) NOT NULL DEFAULT '0',
+ `budgetUnit` char(30) NOT NULL DEFAULT 'CNY',
+ `attribute` varchar(30) NOT NULL DEFAULT '',
+ `percent` float unsigned NOT NULL DEFAULT 0,
+ `milestone` enum('0','1') NOT NULL DEFAULT '0',
+ `output` text DEFAULT NULL,
+ `auth` char(30) NOT NULL DEFAULT '',
+ `storyType` char(30) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` varchar(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(90) NOT NULL DEFAULT '',
+ `code` varchar(45) NOT NULL DEFAULT '',
+ `hasProduct` tinyint(1) unsigned NOT NULL DEFAULT 1,
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `firstEnd` date DEFAULT NULL,
+ `realBegan` date DEFAULT NULL,
+ `realEnd` date DEFAULT NULL,
+ `days` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `status` varchar(10) NOT NULL DEFAULT '',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `pri` enum('1','2','3','4') NOT NULL DEFAULT '1',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `parentVersion` smallint(6) NOT NULL DEFAULT 0,
+ `planDuration` int(11) NOT NULL DEFAULT 0,
+ `realDuration` int(11) NOT NULL DEFAULT 0,
+ `progress` decimal(5,2) NOT NULL DEFAULT 0.00,
+ `estimate` float NOT NULL DEFAULT 0,
+ `left` float NOT NULL DEFAULT 0,
+ `consumed` float NOT NULL DEFAULT 0,
+ `teamCount` int(11) NOT NULL DEFAULT 0,
+ `market` mediumint(8) NOT NULL DEFAULT 0,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `openedVersion` varchar(20) NOT NULL DEFAULT '',
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(20) NOT NULL DEFAULT '',
+ `canceledBy` varchar(30) NOT NULL DEFAULT '',
+ `canceledDate` datetime DEFAULT NULL,
+ `suspendedDate` date DEFAULT NULL,
+ `PO` varchar(30) NOT NULL DEFAULT '',
+ `PM` varchar(30) NOT NULL DEFAULT '',
+ `QD` varchar(30) NOT NULL DEFAULT '',
+ `RD` varchar(30) NOT NULL DEFAULT '',
+ `team` varchar(90) NOT NULL DEFAULT '',
+ `acl` char(30) NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `order` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `stageBy` enum('project','product') NOT NULL DEFAULT 'product',
+ `displayCards` smallint(6) NOT NULL DEFAULT 0,
+ `fluidBoard` enum('0','1') NOT NULL DEFAULT '0',
+ `multiple` enum('0','1') NOT NULL DEFAULT '1',
+ `parallel` mediumint(9) NOT NULL DEFAULT 0,
+ `enabled` enum('on','off') NOT NULL DEFAULT 'on',
+ `colWidth` smallint(6) NOT NULL DEFAULT 264,
+ `minColWidth` smallint(6) NOT NULL DEFAULT 200,
+ `maxColWidth` smallint(6) NOT NULL DEFAULT 384,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `parent` (`parent`),
+ KEY `begin` (`begin`),
+ KEY `end` (`end`),
+ KEY `status` (`status`),
+ KEY `acl` (`acl`),
+ KEY `order` (`order`),
+ KEY `project` (`project`),
+ KEY `type_order` (`type`,`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_projectadmin` (
+ `group` smallint(6) NOT NULL DEFAULT 0,
+ `account` char(30) NOT NULL DEFAULT '',
+ `programs` text DEFAULT NULL,
+ `projects` text DEFAULT NULL,
+ `products` text DEFAULT NULL,
+ `executions` text DEFAULT NULL,
+ UNIQUE KEY `group_account` (`group`,`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_projectcase` (
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `count` mediumint(8) unsigned NOT NULL DEFAULT 1,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `order` smallint(6) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `project` (`project`,`case`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_projectproduct` (
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `plan` varchar(255) NOT NULL DEFAULT '',
+ `roadmap` varchar(255) NOT NULL DEFAULT '',
+ PRIMARY KEY (`project`,`product`,`branch`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_projectspec` (
+ `project` mediumint(8) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `milestone` enum('0','1') NOT NULL DEFAULT '0',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ UNIQUE KEY `project` (`project`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_projectstory` (
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `order` smallint(6) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `project` (`project`,`story`),
+ KEY `story` (`story`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_queue` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `cron` mediumint(9) NOT NULL,
+ `type` varchar(255) NOT NULL,
+ `command` text NOT NULL,
+ `status` enum('wait','doing','done') NOT NULL DEFAULT 'wait',
+ `execId` int(11) DEFAULT NULL,
+ `createdDate` datetime NOT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_relation` (
+ `id` int(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) NOT NULL DEFAULT 0,
+ `product` mediumint(8) NOT NULL DEFAULT 0,
+ `execution` mediumint(8) NOT NULL DEFAULT 0,
+ `AType` char(30) NOT NULL DEFAULT '',
+ `AID` mediumint(8) NOT NULL DEFAULT 0,
+ `AVersion` char(30) NOT NULL DEFAULT '',
+ `relation` char(30) NOT NULL DEFAULT '',
+ `BType` char(30) NOT NULL DEFAULT '',
+ `BID` mediumint(8) NOT NULL DEFAULT 0,
+ `BVersion` char(30) NOT NULL DEFAULT '',
+ `extra` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `relation` (`product`,`relation`,`AType`,`BType`,`AID`,`BID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_relationoftasks` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `execution` mediumint(8) unsigned NOT NULL,
+ `pretask` mediumint(8) unsigned NOT NULL,
+ `condition` enum('begin','end') NOT NULL,
+ `task` mediumint(8) unsigned NOT NULL,
+ `action` enum('begin','end') NOT NULL,
+ PRIMARY KEY (`id`),
+ KEY `relationoftasks` (`execution`,`task`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_release` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` varchar(255) NOT NULL DEFAULT '0',
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` varchar(255) NOT NULL DEFAULT '0',
+ `shadow` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `build` varchar(255) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `marker` enum('0','1') NOT NULL DEFAULT '0',
+ `date` date DEFAULT NULL,
+ `releasedDate` date DEFAULT NULL,
+ `stories` text DEFAULT NULL,
+ `bugs` text DEFAULT NULL,
+ `leftBugs` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `mailto` text DEFAULT NULL,
+ `notify` varchar(255) NOT NULL DEFAULT '',
+ `status` varchar(20) NOT NULL DEFAULT 'normal',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `build` (`build`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_repo` (
+ `id` mediumint(9) NOT NULL AUTO_INCREMENT,
+ `product` varchar(255) NOT NULL DEFAULT '',
+ `projects` varchar(255) NOT NULL DEFAULT '',
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `path` varchar(255) NOT NULL DEFAULT '',
+ `prefix` varchar(100) NOT NULL DEFAULT '',
+ `encoding` varchar(20) NOT NULL DEFAULT '',
+ `SCM` varchar(10) NOT NULL DEFAULT '',
+ `client` varchar(100) NOT NULL DEFAULT '',
+ `serviceHost` varchar(50) NOT NULL DEFAULT '',
+ `serviceProject` varchar(100) NOT NULL DEFAULT '',
+ `commits` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `password` varchar(30) NOT NULL DEFAULT '',
+ `encrypt` varchar(30) NOT NULL DEFAULT 'plain',
+ `acl` text DEFAULT NULL,
+ `synced` tinyint(1) NOT NULL DEFAULT 0,
+ `lastSync` datetime DEFAULT NULL,
+ `lastCommit` datetime DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `extra` char(30) NOT NULL DEFAULT '',
+ `preMerge` enum('0','1') NOT NULL DEFAULT '0',
+ `job` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fileServerUrl` text DEFAULT NULL,
+ `fileServerAccount` varchar(40) NOT NULL DEFAULT '',
+ `fileServerPassword` varchar(100) NOT NULL DEFAULT '',
+ `deleted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_repobranch` (
+ `repo` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `revision` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` varchar(255) NOT NULL DEFAULT '',
+ UNIQUE KEY `repo_revision_branch` (`repo`,`revision`,`branch`),
+ KEY `branch` (`branch`),
+ KEY `revision` (`revision`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_repofiles` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `repo` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `revision` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` varchar(255) NOT NULL DEFAULT '',
+ `oldPath` varchar(255) NOT NULL DEFAULT '',
+ `parent` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT '',
+ `action` char(1) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ KEY `path` (`path`),
+ KEY `parent` (`parent`),
+ KEY `repo` (`repo`),
+ KEY `revision` (`revision`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_repohistory` (
+ `id` mediumint(9) NOT NULL AUTO_INCREMENT,
+ `repo` mediumint(9) NOT NULL DEFAULT 0,
+ `revision` varchar(40) NOT NULL DEFAULT '',
+ `commit` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `comment` text DEFAULT NULL,
+ `committer` varchar(100) NOT NULL DEFAULT '',
+ `time` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `repo` (`repo`),
+ KEY `revision` (`revision`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_report` (
+ `id` mediumint(9) NOT NULL AUTO_INCREMENT,
+ `code` varchar(100) NOT NULL DEFAULT '',
+ `name` text DEFAULT NULL,
+ `dimension` int(8) NOT NULL DEFAULT 0,
+ `module` varchar(100) NOT NULL DEFAULT '',
+ `sql` text DEFAULT NULL,
+ `vars` text DEFAULT NULL,
+ `langs` text DEFAULT NULL,
+ `params` text DEFAULT NULL,
+ `step` tinyint(1) NOT NULL DEFAULT 2,
+ `desc` text DEFAULT NULL,
+ `addedBy` char(30) NOT NULL DEFAULT '',
+ `addedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `code` (`code`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_researchplan` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `customer` varchar(255) NOT NULL DEFAULT '',
+ `stakeholder` varchar(255) NOT NULL DEFAULT '',
+ `objective` varchar(255) NOT NULL DEFAULT '',
+ `begin` datetime DEFAULT NULL,
+ `end` datetime DEFAULT NULL,
+ `location` varchar(255) NOT NULL DEFAULT '',
+ `team` varchar(255) NOT NULL DEFAULT '',
+ `method` enum('','videoConference','interview','questionnaire','telephoneInterview') NOT NULL DEFAULT '',
+ `outline` mediumtext DEFAULT NULL,
+ `schedule` mediumtext DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_researchreport` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `relatedPlan` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `author` varchar(30) NOT NULL DEFAULT '',
+ `content` mediumtext DEFAULT NULL,
+ `customer` varchar(255) NOT NULL DEFAULT '',
+ `researchObjects` varchar(255) NOT NULL DEFAULT '',
+ `begin` datetime DEFAULT NULL,
+ `end` datetime DEFAULT NULL,
+ `location` varchar(255) NOT NULL DEFAULT '',
+ `method` enum('','videoConference','interview','questionnaire','telephoneInterview') NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_review` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `object` mediumint(8) NOT NULL DEFAULT 0,
+ `template` mediumint(8) NOT NULL DEFAULT 0,
+ `doc` varchar(255) NOT NULL DEFAULT '',
+ `docVersion` varchar(255) NOT NULL DEFAULT '',
+ `status` char(30) NOT NULL DEFAULT '',
+ `reviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `auditedBy` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `begin` date DEFAULT NULL,
+ `deadline` date DEFAULT NULL,
+ `lastReviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `lastReviewedDate` date DEFAULT NULL,
+ `lastAuditedBy` varchar(255) NOT NULL DEFAULT '',
+ `lastAuditedDate` date DEFAULT NULL,
+ `lastEditedBy` varchar(255) NOT NULL DEFAULT '',
+ `lastEditedDate` date DEFAULT NULL,
+ `result` char(30) NOT NULL DEFAULT '',
+ `auditResult` char(30) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_reviewcl` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `object` char(30) NOT NULL DEFAULT '',
+ `category` char(30) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `order` mediumint(8) DEFAULT 0,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_reviewissue` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `review` mediumint(8) NOT NULL DEFAULT 0,
+ `approval` mediumint(8) NOT NULL DEFAULT 0,
+ `injection` mediumint(8) NOT NULL DEFAULT 0,
+ `identify` mediumint(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT 'review',
+ `listID` mediumint(8) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `opinion` mediumtext DEFAULT NULL,
+ `opinionDate` date DEFAULT NULL,
+ `status` char(30) NOT NULL DEFAULT '',
+ `resolution` char(30) NOT NULL DEFAULT '',
+ `resolutionBy` char(30) NOT NULL DEFAULT '',
+ `resolutionDate` date DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_reviewlist` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `object` char(30) NOT NULL DEFAULT '',
+ `category` char(30) NOT NULL DEFAULT '',
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_reviewresult` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `review` mediumint(8) NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT 'review',
+ `result` char(30) NOT NULL DEFAULT '',
+ `opinion` text DEFAULT NULL,
+ `reviewer` char(30) NOT NULL DEFAULT '',
+ `remainIssue` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `consumed` float NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `reviewer` (`review`,`reviewer`,`type`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_risk` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` varchar(255) NOT NULL DEFAULT '',
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `source` char(30) NOT NULL DEFAULT '',
+ `category` char(30) NOT NULL DEFAULT '',
+ `strategy` char(30) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT 'active',
+ `impact` char(30) NOT NULL DEFAULT '',
+ `probability` char(30) NOT NULL DEFAULT '',
+ `rate` char(30) NOT NULL DEFAULT '',
+ `pri` char(30) NOT NULL DEFAULT '',
+ `identifiedDate` date DEFAULT NULL,
+ `prevention` mediumtext DEFAULT NULL,
+ `remedy` mediumtext DEFAULT NULL,
+ `plannedClosedDate` date DEFAULT NULL,
+ `actualClosedDate` date DEFAULT NULL,
+ `lib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `from` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `resolution` mediumtext DEFAULT NULL,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `activateBy` varchar(30) NOT NULL DEFAULT '',
+ `activateDate` date DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` date DEFAULT NULL,
+ `cancelBy` varchar(30) NOT NULL DEFAULT '',
+ `cancelDate` date DEFAULT NULL,
+ `cancelReason` char(30) NOT NULL DEFAULT '',
+ `hangupBy` varchar(30) NOT NULL DEFAULT '',
+ `hangupDate` date DEFAULT NULL,
+ `trackedBy` varchar(30) NOT NULL DEFAULT '',
+ `trackedDate` date DEFAULT NULL,
+ `assignedDate` date DEFAULT NULL,
+ `approvedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_riskissue` (
+ `risk` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `issue` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `risk_issue` (`risk`,`issue`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_roadmap` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) NOT NULL DEFAULT 0,
+ `branch` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `status` char(30) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `desc` longtext DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `closedBy` char(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` enum('done','canceled') DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_roadmapstory` (
+ `roadmap` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `order` mediumint(8) unsigned NOT NULL,
+ UNIQUE KEY `roadmap_story` (`roadmap`,`story`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_scene` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `sort` int(11) unsigned NOT NULL DEFAULT 0,
+ `openedBy` char(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `parent` int(11) NOT NULL DEFAULT 0,
+ `grade` tinyint(3) NOT NULL DEFAULT 0,
+ `path` varchar(1000) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_score` (
+ `id` bigint(12) unsigned NOT NULL AUTO_INCREMENT,
+ `account` varchar(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `method` varchar(30) NOT NULL DEFAULT '',
+ `desc` varchar(250) NOT NULL DEFAULT '',
+ `before` int(11) NOT NULL DEFAULT 0,
+ `score` int(11) NOT NULL DEFAULT 0,
+ `after` int(11) NOT NULL DEFAULT 0,
+ `time` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`),
+ KEY `module` (`module`),
+ KEY `method` (`method`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_screen` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `dimension` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `acl` enum('open','private') NOT NULL DEFAULT 'open',
+ `whitelist` text DEFAULT NULL,
+ `cover` mediumtext DEFAULT NULL,
+ `scheme` mediumtext DEFAULT NULL,
+ `status` enum('draft','published') NOT NULL DEFAULT 'draft',
+ `builtin` enum('0','1') NOT NULL DEFAULT '0',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_searchdict` (
+ `key` smallint(6) unsigned NOT NULL DEFAULT 0,
+ `value` char(3) NOT NULL DEFAULT '',
+ PRIMARY KEY (`key`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_searchindex` (
+ `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `objectType` char(20) NOT NULL DEFAULT '',
+ `objectID` mediumint(9) NOT NULL DEFAULT 0,
+ `title` text DEFAULT NULL,
+ `content` text DEFAULT NULL,
+ `addedDate` datetime DEFAULT NULL,
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `object` (`objectType`,`objectID`),
+ KEY `addedDate` (`addedDate`),
+ FULLTEXT KEY `title_content` (`title`,`content`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_serverroom` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(128) NOT NULL DEFAULT '',
+ `city` varchar(128) NOT NULL DEFAULT '',
+ `line` varchar(20) NOT NULL DEFAULT '',
+ `bandwidth` varchar(128) NOT NULL DEFAULT '',
+ `provider` varchar(128) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_service` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `external` enum('0','1') NOT NULL DEFAULT '0',
+ `port` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `entry` varchar(255) NOT NULL DEFAULT '',
+ `deploy` varchar(255) NOT NULL DEFAULT '',
+ `version` varchar(64) NOT NULL DEFAULT '',
+ `color` char(7) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `dept` varchar(128) NOT NULL DEFAULT '',
+ `devel` varchar(30) NOT NULL DEFAULT '',
+ `qa` varchar(30) NOT NULL DEFAULT '',
+ `ops` varchar(30) NOT NULL DEFAULT '',
+ `hosts` text DEFAULT NULL,
+ `softName` varchar(128) NOT NULL DEFAULT '',
+ `softVersion` varchar(128) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_session` (
+ `id` varchar(32) NOT NULL,
+ `data` mediumtext DEFAULT NULL,
+ `timestamp` int(10) unsigned DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `timestamp` (`timestamp`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_solution` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` char(50) NOT NULL DEFAULT '',
+ `appID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `appName` char(50) NOT NULL DEFAULT '',
+ `appVersion` char(20) NOT NULL DEFAULT '',
+ `version` char(50) NOT NULL DEFAULT '',
+ `chart` char(50) NOT NULL DEFAULT '',
+ `cover` varchar(255) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `introduction` varchar(255) NOT NULL DEFAULT '',
+ `source` char(20) NOT NULL DEFAULT '',
+ `channel` char(20) NOT NULL DEFAULT '',
+ `components` text DEFAULT NULL,
+ `status` char(20) NOT NULL DEFAULT '',
+ `deleted` tinyint(1) NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdAt` datetime DEFAULT NULL,
+ `updatedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_solutions` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `contents` text NOT NULL,
+ `support` text NOT NULL,
+ `measures` text NOT NULL,
+ `type` char(30) NOT NULL DEFAULT '',
+ `addedBy` varchar(30) NOT NULL DEFAULT '',
+ `addedDate` date DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_space` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(200) NOT NULL,
+ `k8space` char(64) NOT NULL,
+ `owner` char(30) NOT NULL,
+ `default` tinyint(1) NOT NULL DEFAULT 0,
+ `createdAt` datetime DEFAULT NULL,
+ `deleted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `name` (`name`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_sqlbuilder` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `objectID` mediumint(8) NOT NULL,
+ `objectType` varchar(50) NOT NULL,
+ `sql` text DEFAULT NULL,
+ `setting` text DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_sqlview` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(90) NOT NULL DEFAULT '',
+ `code` varchar(45) NOT NULL DEFAULT '',
+ `sql` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_stage` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `percent` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `projectType` varchar(255) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_stakeholder` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `objectID` mediumint(8) NOT NULL DEFAULT 0,
+ `objectType` char(30) NOT NULL DEFAULT '',
+ `user` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `key` enum('0','1') NOT NULL DEFAULT '0',
+ `from` char(30) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `objectID` (`objectID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_story` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `parent` mediumint(9) NOT NULL DEFAULT 0,
+ `isParent` enum('0','1') NOT NULL DEFAULT '0',
+ `root` mediumint(9) NOT NULL DEFAULT 0,
+ `path` text DEFAULT NULL,
+ `grade` smallint(6) NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `plan` text DEFAULT NULL,
+ `source` varchar(20) NOT NULL DEFAULT '',
+ `sourceNote` varchar(255) NOT NULL DEFAULT '',
+ `fromBug` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `feedback` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT 'story',
+ `category` varchar(30) NOT NULL DEFAULT 'feature',
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 3,
+ `estimate` float unsigned NOT NULL DEFAULT 0,
+ `status` enum('','changing','active','draft','closed','reviewing','launched','developing') NOT NULL DEFAULT '',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `color` char(7) NOT NULL DEFAULT '',
+ `stage` enum('','wait','inroadmap','incharter','planned','projected','designing','designed','developing','developed','testing','tested','verified','rejected','delivering','delivered','released','closed') NOT NULL DEFAULT 'wait',
+ `stagedBy` char(30) NOT NULL DEFAULT '',
+ `mailto` text DEFAULT NULL,
+ `lib` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromStory` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromVersion` smallint(6) NOT NULL DEFAULT 1,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `approvedDate` date DEFAULT NULL,
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `changedBy` varchar(30) NOT NULL DEFAULT '',
+ `changedDate` datetime DEFAULT NULL,
+ `reviewedBy` varchar(255) NOT NULL DEFAULT '',
+ `reviewedDate` datetime DEFAULT NULL,
+ `releasedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `toBug` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `linkStories` varchar(255) NOT NULL DEFAULT '',
+ `linkRequirements` varchar(255) NOT NULL DEFAULT '',
+ `twins` varchar(255) NOT NULL DEFAULT '',
+ `duplicateStory` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 1,
+ `parentVersion` smallint(6) NOT NULL DEFAULT 0,
+ `demandVersion` smallint(6) NOT NULL DEFAULT 0,
+ `storyChanged` enum('0','1') NOT NULL DEFAULT '0',
+ `feedbackBy` varchar(100) NOT NULL DEFAULT '',
+ `notifyEmail` varchar(100) NOT NULL DEFAULT '',
+ `BSA` char(30) NOT NULL DEFAULT '',
+ `duration` char(30) NOT NULL DEFAULT '',
+ `demand` mediumint(8) NOT NULL DEFAULT 0,
+ `submitedBy` varchar(30) NOT NULL DEFAULT '',
+ `roadmap` varchar(255) NOT NULL DEFAULT '',
+ `URChanged` enum('0','1') NOT NULL DEFAULT '0',
+ `unlinkReason` enum('','omit','other') NOT NULL DEFAULT '',
+ `retractedReason` enum('','omit','other') NOT NULL DEFAULT '',
+ `retractedBy` varchar(30) NOT NULL DEFAULT '',
+ `retractedDate` datetime DEFAULT NULL,
+ `verifiedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `root` (`root`),
+ KEY `status` (`status`),
+ KEY `assignedTo` (`assignedTo`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_storyestimate` (
+ `story` mediumint(9) NOT NULL DEFAULT 0,
+ `round` smallint(6) NOT NULL DEFAULT 0,
+ `estimate` text DEFAULT NULL,
+ `average` float NOT NULL DEFAULT 0,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ UNIQUE KEY `story` (`story`,`round`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_storygrade` (
+ `type` enum('story','requirement','epic') NOT NULL,
+ `grade` smallint(6) NOT NULL,
+ `name` char(30) NOT NULL,
+ `status` char(30) NOT NULL
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_storyreview` (
+ `story` mediumint(9) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `reviewer` varchar(30) NOT NULL DEFAULT '',
+ `result` varchar(30) NOT NULL DEFAULT '',
+ `reviewDate` datetime DEFAULT NULL,
+ UNIQUE KEY `story` (`story`,`version`,`reviewer`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_storyspec` (
+ `story` mediumint(9) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `spec` mediumtext DEFAULT NULL,
+ `verify` mediumtext DEFAULT NULL,
+ `files` text DEFAULT NULL,
+ UNIQUE KEY `story` (`story`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_storystage` (
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `branch` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `stage` varchar(50) NOT NULL DEFAULT '',
+ `stagedBy` char(30) NOT NULL DEFAULT '',
+ UNIQUE KEY `story_branch` (`story`,`branch`),
+ KEY `story` (`story`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_suitecase` (
+ `suite` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(5) unsigned NOT NULL DEFAULT 0,
+ UNIQUE KEY `suitecase` (`suite`,`case`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_task` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `parent` mediumint(8) NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `design` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `story` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `storyVersion` smallint(6) NOT NULL DEFAULT 1,
+ `designVersion` smallint(6) unsigned NOT NULL DEFAULT 1,
+ `fromBug` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `feedback` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `fromIssue` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT '',
+ `mode` varchar(10) NOT NULL DEFAULT '',
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `estimate` float unsigned NOT NULL DEFAULT 0,
+ `consumed` float unsigned NOT NULL DEFAULT 0,
+ `left` float unsigned NOT NULL DEFAULT 0,
+ `deadline` date DEFAULT NULL,
+ `status` enum('wait','doing','done','pause','cancel','closed') NOT NULL DEFAULT 'wait',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `color` char(7) NOT NULL DEFAULT '',
+ `mailto` text DEFAULT NULL,
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `estStarted` date DEFAULT NULL,
+ `realStarted` datetime DEFAULT NULL,
+ `finishedBy` varchar(30) NOT NULL DEFAULT '',
+ `finishedDate` datetime DEFAULT NULL,
+ `finishedList` text DEFAULT NULL,
+ `canceledBy` varchar(30) NOT NULL DEFAULT '',
+ `canceledDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `planDuration` int(11) NOT NULL DEFAULT 0,
+ `realDuration` int(11) NOT NULL DEFAULT 0,
+ `closedReason` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedBy` varchar(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `activatedDate` datetime DEFAULT NULL,
+ `order` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `repo` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `mr` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `entry` varchar(255) NOT NULL DEFAULT '',
+ `lines` varchar(10) NOT NULL DEFAULT '',
+ `v1` varchar(40) NOT NULL DEFAULT '',
+ `v2` varchar(40) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ PRIMARY KEY (`id`),
+ KEY `execution` (`execution`),
+ KEY `story` (`story`),
+ KEY `parent` (`parent`),
+ KEY `assignedTo` (`assignedTo`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_taskestimate` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `task` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `date` date DEFAULT NULL,
+ `left` float unsigned NOT NULL DEFAULT 0,
+ `consumed` float unsigned NOT NULL DEFAULT 0,
+ `account` char(30) NOT NULL DEFAULT '',
+ `work` text DEFAULT NULL,
+ `order` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `task` (`task`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_taskspec` (
+ `task` mediumint(8) NOT NULL DEFAULT 0,
+ `version` smallint(6) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `estStarted` date DEFAULT NULL,
+ `deadline` date DEFAULT NULL,
+ UNIQUE KEY `task` (`task`,`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_taskteam` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `task` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` char(30) NOT NULL DEFAULT '',
+ `estimate` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `consumed` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `left` decimal(12,2) NOT NULL DEFAULT 0.00,
+ `transfer` char(30) NOT NULL DEFAULT '',
+ `status` enum('wait','doing','done') NOT NULL DEFAULT 'wait',
+ `order` tinyint(3) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `task` (`task`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_team` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `root` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `type` enum('project','task','execution') NOT NULL DEFAULT 'project',
+ `account` char(30) NOT NULL DEFAULT '',
+ `role` char(30) NOT NULL DEFAULT '',
+ `position` varchar(30) NOT NULL DEFAULT '',
+ `limited` char(8) NOT NULL DEFAULT 'no',
+ `join` date DEFAULT NULL,
+ `days` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `hours` float(3,1) unsigned NOT NULL DEFAULT 0.0,
+ `estimate` decimal(12,2) unsigned NOT NULL DEFAULT 0.00,
+ `consumed` decimal(12,2) unsigned NOT NULL DEFAULT 0.00,
+ `left` decimal(12,2) unsigned NOT NULL DEFAULT 0.00,
+ `order` tinyint(3) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `team` (`root`,`type`,`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_testreport` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `tasks` varchar(255) NOT NULL DEFAULT '',
+ `builds` varchar(255) NOT NULL DEFAULT '',
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `owner` char(30) NOT NULL DEFAULT '',
+ `members` text DEFAULT NULL,
+ `stories` text DEFAULT NULL,
+ `bugs` text DEFAULT NULL,
+ `cases` text DEFAULT NULL,
+ `report` text DEFAULT NULL,
+ `objectType` varchar(20) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_testresult` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `run` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `job` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `compile` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `caseResult` char(30) NOT NULL DEFAULT '',
+ `stepResults` text DEFAULT NULL,
+ `ZTFResult` text DEFAULT NULL,
+ `node` int(8) unsigned NOT NULL DEFAULT 0,
+ `lastRunner` varchar(30) NOT NULL DEFAULT '',
+ `date` datetime DEFAULT NULL,
+ `duration` float NOT NULL DEFAULT 0,
+ `xml` text DEFAULT NULL,
+ `deploy` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `case` (`case`),
+ KEY `version` (`version`),
+ KEY `run` (`run`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_testrun` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `task` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `case` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `version` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `assignedTo` char(30) NOT NULL DEFAULT '',
+ `lastRunner` varchar(30) NOT NULL DEFAULT '',
+ `lastRunDate` datetime DEFAULT NULL,
+ `lastRunResult` char(30) NOT NULL DEFAULT '',
+ `status` char(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `task` (`task`,`case`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_testsuite` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `type` varchar(20) NOT NULL DEFAULT '',
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `addedBy` char(30) NOT NULL DEFAULT '',
+ `addedDate` datetime DEFAULT NULL,
+ `lastEditedBy` char(30) NOT NULL DEFAULT '',
+ `lastEditedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_testtask` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` char(90) NOT NULL DEFAULT '',
+ `execution` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `build` char(30) NOT NULL DEFAULT '',
+ `type` varchar(255) NOT NULL DEFAULT '',
+ `owner` varchar(30) NOT NULL DEFAULT '',
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `realBegan` date DEFAULT NULL,
+ `realFinishedDate` datetime DEFAULT NULL,
+ `mailto` text DEFAULT NULL,
+ `desc` mediumtext DEFAULT NULL,
+ `report` text DEFAULT NULL,
+ `status` enum('blocked','doing','wait','done') NOT NULL DEFAULT 'wait',
+ `testreport` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `auto` varchar(10) NOT NULL DEFAULT 'no',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `members` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`),
+ KEY `build` (`build`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ticket` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `product` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `module` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `title` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `openedBuild` varchar(255) NOT NULL DEFAULT '',
+ `feedback` mediumint(8) NOT NULL DEFAULT 0,
+ `assignedTo` varchar(255) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `realStarted` datetime DEFAULT NULL,
+ `startedBy` varchar(255) NOT NULL DEFAULT '',
+ `startedDate` datetime DEFAULT NULL,
+ `deadline` date DEFAULT NULL,
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `estimate` float unsigned NOT NULL DEFAULT 0,
+ `left` float unsigned NOT NULL DEFAULT 0,
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `openedBy` varchar(30) NOT NULL DEFAULT '',
+ `openedDate` datetime DEFAULT NULL,
+ `activatedCount` int(11) NOT NULL DEFAULT 0,
+ `activatedBy` varchar(30) NOT NULL DEFAULT '',
+ `activatedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `closedReason` varchar(30) NOT NULL DEFAULT '',
+ `finishedBy` varchar(30) NOT NULL DEFAULT '',
+ `finishedDate` datetime DEFAULT NULL,
+ `resolvedBy` varchar(30) NOT NULL DEFAULT '',
+ `resolvedDate` datetime DEFAULT NULL,
+ `resolution` text DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `keywords` varchar(255) NOT NULL DEFAULT '',
+ `repeatTicket` mediumint(8) NOT NULL DEFAULT 0,
+ `mailto` varchar(255) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `subStatus` varchar(30) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ KEY `product` (`product`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ticketrelation` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `ticketId` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `objectId` mediumint(8) NOT NULL DEFAULT 0,
+ `objectType` varchar(100) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ KEY `ticketId` (`ticketId`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_ticketsource` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `ticketId` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `customer` varchar(100) NOT NULL DEFAULT '',
+ `contact` varchar(100) NOT NULL DEFAULT '',
+ `notifyEmail` varchar(100) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `ticketId` (`ticketId`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_todo` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `date` date DEFAULT NULL,
+ `begin` smallint(4) unsigned zerofill NOT NULL DEFAULT 0000,
+ `end` smallint(4) unsigned zerofill NOT NULL DEFAULT 0000,
+ `feedback` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `type` char(15) NOT NULL DEFAULT '',
+ `cycle` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `pri` tinyint(3) unsigned NOT NULL DEFAULT 0,
+ `name` char(150) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `status` enum('wait','doing','done','closed') NOT NULL DEFAULT 'wait',
+ `private` tinyint(1) NOT NULL DEFAULT 0,
+ `config` varchar(1000) NOT NULL DEFAULT '',
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedBy` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `finishedBy` varchar(30) NOT NULL DEFAULT '',
+ `finishedDate` datetime DEFAULT NULL,
+ `closedBy` varchar(30) NOT NULL DEFAULT '',
+ `closedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`),
+ KEY `assignedTo` (`assignedTo`),
+ KEY `finishedBy` (`finishedBy`),
+ KEY `date` (`date`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_traincategory` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `name` char(30) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `grade` tinyint(3) NOT NULL DEFAULT 0,
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `parent` (`parent`),
+ KEY `path` (`path`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_traincontents` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `code` varchar(50) NOT NULL DEFAULT '',
+ `course` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `type` varchar(30) NOT NULL DEFAULT '',
+ `parent` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `path` char(255) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `order` mediumint(8) NOT NULL DEFAULT 0,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_traincourse` (
+ `id` mediumint(8) NOT NULL AUTO_INCREMENT,
+ `code` varchar(255) NOT NULL DEFAULT '',
+ `category` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `status` varchar(10) NOT NULL DEFAULT '',
+ `teacher` varchar(30) NOT NULL DEFAULT '',
+ `desc` mediumtext DEFAULT NULL,
+ `importedStatus` enum('','wait','doing','done') NOT NULL DEFAULT '',
+ `lastUpdatedTime` int(10) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(255) NOT NULL DEFAULT '',
+ `createdDate` date DEFAULT NULL,
+ `editedBy` varchar(255) NOT NULL DEFAULT '',
+ `editedDate` date DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_trainplan` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `place` varchar(255) NOT NULL DEFAULT '',
+ `trainee` text DEFAULT NULL,
+ `lecturer` varchar(20) NOT NULL DEFAULT '',
+ `type` enum('inside','outside') NOT NULL DEFAULT 'inside',
+ `status` varchar(20) NOT NULL DEFAULT '',
+ `summary` mediumtext DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_trainrecords` (
+ `user` char(30) NOT NULL DEFAULT '',
+ `objectId` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `objectType` varchar(10) NOT NULL DEFAULT '',
+ `status` varchar(10) NOT NULL DEFAULT '',
+ PRIMARY KEY (`user`,`objectId`,`objectType`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_trip` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` enum('trip','egress') NOT NULL DEFAULT 'trip',
+ `customers` varchar(20) NOT NULL DEFAULT '',
+ `name` char(30) NOT NULL DEFAULT '',
+ `desc` text DEFAULT NULL,
+ `year` char(4) NOT NULL DEFAULT '',
+ `begin` date DEFAULT NULL,
+ `end` date DEFAULT NULL,
+ `start` time DEFAULT NULL,
+ `finish` time DEFAULT NULL,
+ `from` char(50) NOT NULL DEFAULT '',
+ `to` char(50) NOT NULL DEFAULT '',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `year` (`year`),
+ KEY `createdBy` (`createdBy`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_user` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `company` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `type` char(30) NOT NULL DEFAULT 'inside',
+ `dept` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `account` char(30) NOT NULL DEFAULT '',
+ `password` char(32) NOT NULL DEFAULT '',
+ `role` char(10) NOT NULL DEFAULT '',
+ `realname` varchar(100) NOT NULL DEFAULT '',
+ `superior` char(30) DEFAULT '',
+ `pinyin` varchar(255) NOT NULL DEFAULT '',
+ `nickname` char(60) NOT NULL DEFAULT '',
+ `commiter` varchar(100) NOT NULL DEFAULT '',
+ `avatar` text DEFAULT NULL,
+ `birthday` date DEFAULT NULL,
+ `gender` enum('f','m') NOT NULL DEFAULT 'f',
+ `email` char(90) NOT NULL DEFAULT '',
+ `skype` char(90) NOT NULL DEFAULT '',
+ `qq` char(20) NOT NULL DEFAULT '',
+ `mobile` char(11) NOT NULL DEFAULT '',
+ `phone` char(20) NOT NULL DEFAULT '',
+ `weixin` varchar(90) NOT NULL DEFAULT '',
+ `dingding` varchar(90) NOT NULL DEFAULT '',
+ `slack` varchar(90) NOT NULL DEFAULT '',
+ `whatsapp` varchar(90) NOT NULL DEFAULT '',
+ `address` char(120) NOT NULL DEFAULT '',
+ `zipcode` char(10) NOT NULL DEFAULT '',
+ `nature` text DEFAULT NULL,
+ `analysis` text DEFAULT NULL,
+ `strategy` text DEFAULT NULL,
+ `join` date DEFAULT NULL,
+ `visits` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `visions` varchar(20) NOT NULL DEFAULT 'rnd,lite',
+ `ip` varchar(255) NOT NULL DEFAULT '',
+ `last` int(11) unsigned NOT NULL DEFAULT 0,
+ `fails` tinyint(5) NOT NULL DEFAULT 0,
+ `locked` datetime DEFAULT NULL,
+ `feedback` enum('0','1') NOT NULL DEFAULT '0',
+ `ranzhi` char(30) NOT NULL DEFAULT '',
+ `ldap` char(30) NOT NULL DEFAULT '',
+ `score` int(11) NOT NULL DEFAULT 0,
+ `scoreLevel` int(11) NOT NULL DEFAULT 0,
+ `resetToken` varchar(50) NOT NULL DEFAULT '',
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `clientStatus` enum('online','away','busy','offline','meeting') NOT NULL DEFAULT 'offline',
+ `clientLang` varchar(10) NOT NULL DEFAULT 'zh-cn',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `account` (`account`),
+ KEY `dept` (`dept`),
+ KEY `email` (`email`),
+ KEY `commiter` (`commiter`),
+ KEY `deleted` (`deleted`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_usercontact` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `listName` varchar(60) NOT NULL DEFAULT '',
+ `userList` text DEFAULT NULL,
+ `public` tinyint(1) NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_usergroup` (
+ `account` char(30) NOT NULL DEFAULT '',
+ `group` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `project` text DEFAULT NULL,
+ UNIQUE KEY `account` (`account`,`group`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_userquery` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `title` varchar(90) NOT NULL DEFAULT '',
+ `form` text DEFAULT NULL,
+ `sql` text DEFAULT NULL,
+ `shortcut` enum('0','1') NOT NULL DEFAULT '0',
+ `common` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`),
+ KEY `module` (`module`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_usertpl` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `account` char(30) NOT NULL DEFAULT '',
+ `type` char(30) NOT NULL DEFAULT '',
+ `title` varchar(150) NOT NULL DEFAULT '',
+ `content` text DEFAULT NULL,
+ `public` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`),
+ KEY `account` (`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_userview` (
+ `account` char(30) NOT NULL DEFAULT '',
+ `programs` mediumtext DEFAULT NULL,
+ `products` mediumtext DEFAULT NULL,
+ `projects` mediumtext DEFAULT NULL,
+ `sprints` mediumtext DEFAULT NULL,
+ UNIQUE KEY `account` (`account`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_webhook` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` varchar(15) NOT NULL DEFAULT 'default',
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `url` varchar(255) NOT NULL DEFAULT '',
+ `domain` varchar(255) NOT NULL DEFAULT '',
+ `secret` varchar(255) NOT NULL DEFAULT '',
+ `contentType` varchar(30) NOT NULL DEFAULT 'application/json',
+ `sendType` enum('sync','async') NOT NULL DEFAULT 'sync',
+ `products` text DEFAULT NULL,
+ `executions` text DEFAULT NULL,
+ `params` varchar(100) NOT NULL DEFAULT '',
+ `actions` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_weeklyreport` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `weekStart` date DEFAULT NULL,
+ `pv` float(9,2) NOT NULL DEFAULT 0.00,
+ `ev` float(9,2) NOT NULL DEFAULT 0.00,
+ `ac` float(9,2) NOT NULL DEFAULT 0.00,
+ `sv` float(9,2) NOT NULL DEFAULT 0.00,
+ `cv` float(9,2) NOT NULL DEFAULT 0.00,
+ `staff` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `progress` varchar(255) NOT NULL DEFAULT '',
+ `workload` varchar(255) NOT NULL DEFAULT '',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `week` (`project`,`weekStart`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workestimation` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `project` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `scale` decimal(10,2) unsigned NOT NULL DEFAULT 0.00,
+ `productivity` decimal(10,2) unsigned NOT NULL DEFAULT 0.00,
+ `duration` decimal(10,2) unsigned NOT NULL DEFAULT 0.00,
+ `unitLaborCost` decimal(10,2) unsigned NOT NULL DEFAULT 0.00,
+ `totalLaborCost` decimal(10,2) unsigned NOT NULL DEFAULT 0.00,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `assignedTo` varchar(30) NOT NULL DEFAULT '',
+ `assignedDate` datetime DEFAULT NULL,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ `dayHour` decimal(10,2) NOT NULL DEFAULT 0.00,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflow` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `parent` varchar(30) NOT NULL DEFAULT '',
+ `child` varchar(30) NOT NULL DEFAULT '',
+ `type` varchar(10) NOT NULL DEFAULT 'flow',
+ `navigator` varchar(10) NOT NULL DEFAULT '',
+ `app` varchar(20) NOT NULL DEFAULT '',
+ `position` varchar(30) NOT NULL DEFAULT '',
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `table` varchar(50) NOT NULL DEFAULT '',
+ `name` varchar(30) NOT NULL DEFAULT '',
+ `icon` varchar(30) NOT NULL DEFAULT 'flow',
+ `titleField` varchar(30) NOT NULL DEFAULT '',
+ `contentField` text DEFAULT NULL,
+ `flowchart` text DEFAULT NULL,
+ `js` text DEFAULT NULL,
+ `css` text DEFAULT NULL,
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `buildin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `belong` varchar(50) NOT NULL DEFAULT '',
+ `administrator` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `version` varchar(10) NOT NULL DEFAULT '1.0',
+ `status` varchar(10) NOT NULL DEFAULT 'wait',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `approval` enum('enabled','disabled') NOT NULL DEFAULT 'disabled',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`app`,`module`,`vision`),
+ KEY `type` (`type`),
+ KEY `app` (`app`),
+ KEY `module` (`module`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowaction` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `action` varchar(50) NOT NULL DEFAULT '',
+ `method` varchar(50) NOT NULL DEFAULT '',
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `type` enum('single','batch') NOT NULL DEFAULT 'single',
+ `batchMode` enum('same','different') NOT NULL DEFAULT 'different',
+ `extensionType` varchar(10) NOT NULL DEFAULT 'override',
+ `open` varchar(20) NOT NULL DEFAULT '',
+ `position` enum('menu','browseandview','browse','view') NOT NULL DEFAULT 'browseandview',
+ `layout` char(20) NOT NULL DEFAULT '',
+ `show` enum('dropdownlist','direct') NOT NULL DEFAULT 'dropdownlist',
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `buildin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `role` varchar(10) NOT NULL DEFAULT 'custom',
+ `virtual` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `conditions` text DEFAULT NULL,
+ `verifications` text DEFAULT NULL,
+ `hooks` text DEFAULT NULL,
+ `linkages` text DEFAULT NULL,
+ `js` text DEFAULT NULL,
+ `css` text DEFAULT NULL,
+ `toList` char(255) NOT NULL DEFAULT '',
+ `blocks` text DEFAULT NULL,
+ `desc` text DEFAULT NULL,
+ `status` varchar(10) NOT NULL DEFAULT 'enable',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`module`,`action`,`vision`),
+ KEY `module` (`module`),
+ KEY `action` (`action`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowdatasource` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` enum('system','sql','func','option','lang','category') NOT NULL DEFAULT 'option',
+ `name` varchar(30) NOT NULL DEFAULT '',
+ `code` varchar(30) NOT NULL DEFAULT '',
+ `datasource` text DEFAULT NULL,
+ `view` varchar(20) NOT NULL DEFAULT '',
+ `keyField` varchar(50) NOT NULL DEFAULT '',
+ `valueField` varchar(50) NOT NULL DEFAULT '',
+ `buildin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `type` (`type`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowfield` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `field` varchar(50) NOT NULL DEFAULT '',
+ `type` varchar(20) NOT NULL DEFAULT 'varchar',
+ `length` varchar(10) NOT NULL DEFAULT '',
+ `name` varchar(50) NOT NULL DEFAULT '',
+ `control` varchar(20) NOT NULL DEFAULT '',
+ `expression` text DEFAULT NULL,
+ `options` text DEFAULT NULL,
+ `default` varchar(100) NOT NULL DEFAULT '',
+ `rules` varchar(255) NOT NULL DEFAULT '',
+ `placeholder` varchar(100) NOT NULL DEFAULT '',
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `searchOrder` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `exportOrder` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `canExport` enum('0','1') NOT NULL DEFAULT '0',
+ `canSearch` enum('0','1') NOT NULL DEFAULT '0',
+ `isValue` enum('0','1') NOT NULL DEFAULT '0',
+ `readonly` enum('0','1') NOT NULL DEFAULT '0',
+ `buildin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `role` varchar(10) NOT NULL DEFAULT 'custom',
+ `desc` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`module`,`field`),
+ KEY `module` (`module`),
+ KEY `field` (`field`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowlabel` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `action` varchar(30) NOT NULL DEFAULT 'browse',
+ `code` varchar(30) NOT NULL DEFAULT '',
+ `label` varchar(255) NOT NULL DEFAULT '',
+ `params` text DEFAULT NULL,
+ `orderBy` text DEFAULT NULL,
+ `order` tinyint(3) NOT NULL DEFAULT 0,
+ `buildin` tinyint(1) unsigned NOT NULL DEFAULT 0,
+ `role` varchar(10) NOT NULL DEFAULT 'custom',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `module` (`module`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowlayout` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `action` varchar(50) NOT NULL DEFAULT '',
+ `ui` mediumint(8) NOT NULL DEFAULT 0,
+ `field` varchar(50) NOT NULL DEFAULT '',
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `width` varchar(50) NOT NULL DEFAULT '0',
+ `position` text DEFAULT NULL,
+ `readonly` enum('0','1') NOT NULL DEFAULT '0',
+ `mobileShow` enum('0','1') NOT NULL DEFAULT '1',
+ `summary` varchar(20) NOT NULL DEFAULT '',
+ `defaultValue` text DEFAULT NULL,
+ `layoutRules` varchar(255) NOT NULL DEFAULT '',
+ `vision` varchar(10) NOT NULL DEFAULT 'rnd',
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`module`,`action`,`ui`,`field`,`vision`),
+ KEY `module` (`module`),
+ KEY `action` (`action`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowlinkdata` (
+ `objectType` varchar(30) NOT NULL DEFAULT '',
+ `objectID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `linkedType` varchar(30) NOT NULL DEFAULT '',
+ `linkedID` mediumint(8) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ UNIQUE KEY `unique` (`objectType`,`objectID`,`linkedType`,`linkedID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowrelation` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `prev` varchar(30) NOT NULL DEFAULT '',
+ `next` varchar(30) NOT NULL DEFAULT '',
+ `field` varchar(50) NOT NULL DEFAULT '',
+ `actions` varchar(20) NOT NULL DEFAULT '',
+ `actionCodes` text DEFAULT NULL,
+ `buildin` enum('0','1') NOT NULL DEFAULT '0',
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowrelationlayout` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `prev` varchar(30) NOT NULL DEFAULT '',
+ `next` varchar(30) NOT NULL DEFAULT '',
+ `action` varchar(50) NOT NULL DEFAULT '',
+ `ui` mediumint(8) NOT NULL DEFAULT 0,
+ `field` varchar(50) NOT NULL DEFAULT '',
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `unique` (`prev`,`next`,`action`,`ui`,`field`),
+ KEY `prev` (`prev`),
+ KEY `next` (`next`),
+ KEY `action` (`action`),
+ KEY `order` (`order`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowreport` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL,
+ `name` varchar(100) NOT NULL,
+ `type` enum('pie','line','bar') NOT NULL DEFAULT 'pie',
+ `countType` enum('sum','count') NOT NULL DEFAULT 'sum',
+ `displayType` enum('value','percent') NOT NULL DEFAULT 'value',
+ `dimension` varchar(130) NOT NULL,
+ `fields` text NOT NULL,
+ `order` smallint(5) unsigned NOT NULL DEFAULT 0,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowrule` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `type` enum('system','regex','func') NOT NULL DEFAULT 'regex',
+ `name` varchar(30) NOT NULL DEFAULT '',
+ `rule` text DEFAULT NULL,
+ `createdBy` char(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` char(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `type` (`type`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowsql` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `field` varchar(50) NOT NULL DEFAULT '',
+ `action` varchar(50) NOT NULL DEFAULT '',
+ `sql` text DEFAULT NULL,
+ `vars` text DEFAULT NULL,
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `module` (`module`),
+ KEY `field` (`field`),
+ KEY `action` (`action`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowui` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL,
+ `action` varchar(50) NOT NULL,
+ `name` varchar(30) NOT NULL,
+ `conditions` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ KEY `module` (`module`),
+ KEY `action` (`action`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_workflowversion` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `module` varchar(30) NOT NULL DEFAULT '',
+ `version` varchar(10) NOT NULL DEFAULT '',
+ `fields` text DEFAULT NULL,
+ `actions` text DEFAULT NULL,
+ `layouts` text DEFAULT NULL,
+ `sqls` text DEFAULT NULL,
+ `labels` text DEFAULT NULL,
+ `table` text DEFAULT NULL,
+ `datas` text DEFAULT NULL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `moduleversion` (`module`,`version`),
+ KEY `module` (`module`),
+ KEY `version` (`version`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+CREATE TABLE `zt_zoutput` (
+ `id` mediumint(8) unsigned NOT NULL AUTO_INCREMENT,
+ `activity` mediumint(8) NOT NULL DEFAULT 0,
+ `name` varchar(255) NOT NULL DEFAULT '',
+ `content` mediumtext DEFAULT NULL,
+ `optional` char(20) NOT NULL DEFAULT '',
+ `tailorNorm` varchar(255) NOT NULL DEFAULT '',
+ `status` varchar(30) NOT NULL DEFAULT '',
+ `createdBy` varchar(30) NOT NULL DEFAULT '',
+ `createdDate` datetime DEFAULT NULL,
+ `editedBy` varchar(30) NOT NULL DEFAULT '',
+ `editedDate` datetime DEFAULT NULL,
+ `order` mediumint(8) DEFAULT 0,
+ `deleted` enum('0','1') NOT NULL DEFAULT '0',
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8;
diff --git a/db/update20.6.sql b/db/update20.6.sql
index b724e87556..ca5a05aed2 100644
--- a/db/update20.6.sql
+++ b/db/update20.6.sql
@@ -30,7 +30,8 @@ CREATE TABLE IF NOT EXISTS `zt_sqlbuilder` (
DELETE t1
FROM `zt_workflowlayout` t1
LEFT JOIN `zt_workflowfield` t2 ON t1.field = t2.field AND t1.module = t2.module
-WHERE t2.buildin = '1' AND t2.role = 'buildin';
+LEFT JOIN `zt_workflowaction` t3 ON t1.module = t3.module AND t1.action = t3.action
+WHERE t2.buildin = '1' AND t2.role = 'buildin' AND t3.buildin = '1';
ALTER TABLE `zt_dataview` ADD `mode` enum('text', 'builder') not NULL default 'builder' AFTER `code`;
UPDATE `zt_dataview` SET `mode` = 'text';
diff --git a/db/update20.7.sql b/db/update20.7.sql
index c7a38ee54a..ad5613aca3 100644
--- a/db/update20.7.sql
+++ b/db/update20.7.sql
@@ -28,3 +28,14 @@ CREATE INDEX `deleted` ON `zt_metriclib` (`deleted`);
ALTER TABLE `zt_pipeline` ADD `instanceID` mediumint(8) unsigned NOT NULL DEFAULT '0' AFTER `private`;
ALTER TABLE `zt_mr` ADD `isFlow` ENUM('0', '1') NOT NULL DEFAULT '0' AFTER `squash`;
+
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'task', 'recordWorkhour' FROM `zt_grouppriv` WHERE `module` = 'task' AND `method` = 'recordEstimate';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'task', 'editEffort' FROM `zt_grouppriv` WHERE `module` = 'task' AND `method` = 'editEstimate';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'task', 'deleteWorkhour' FROM `zt_grouppriv` WHERE `module` = 'task' AND `method` = 'deleteEstimate';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'bug', 'confirm' FROM `zt_grouppriv` WHERE `module` = 'bug' AND `method` = 'confirmBug';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'testcase', 'batchChangeType' FROM `zt_grouppriv` WHERE `module` = 'testcase' AND `method` = 'batchCaseTypeChange';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'ops', 'provider' FROM `zt_grouppriv` WHERE `module` = 'ops' AND `method` = 'provide';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'projectstory', 'importToLib' FROM `zt_grouppriv` WHERE `module` = 'story' AND `method` = 'importToLib';
+REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) SELECT `group`, 'projectstory', 'batchImportToLib' FROM `zt_grouppriv` WHERE `module` = 'story' AND `method` = 'batchImportToLib';
+
+CREATE UNIQUE INDEX `account_openID` ON `zt_oauth`(`account`,`openID`,`providerType`,`providerID`);
diff --git a/db/updatefunctions.sql b/db/updatefunctions.sql
deleted file mode 100644
index d02da21af7..0000000000
--- a/db/updatefunctions.sql
+++ /dev/null
@@ -1,437 +0,0 @@
-USE `__TABLE__`;
-
-DROP FUNCTION IF EXISTS `get_monday`;
-CREATE FUNCTION `get_monday`(day date) RETURNS date
- begin if date_format(day, '%w') = 0 then return subdate(day, date_format(day, '%w') - 6)__DELIMITER__
- else return subdate(day, date_format(day, '%w') -1)__DELIMITER__
- end if__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `get_sunday`;
-CREATE FUNCTION `get_sunday`(day date) RETURNS date
-begin
- if date_format(day, '%w') = 0 then return day__DELIMITER__
- else return subdate(day, date_format(day, '%w') - 7)__DELIMITER__
- end if__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_cminited`;
-CREATE FUNCTION qc_cminited($project int, $category varchar(30)) returns int
-begin
- declare products int default 0__DELIMITER__
- declare objects int default 0__DELIMITER__
- select COUNT(1) from zt_projectproduct where project = $project into products__DELIMITER__
- select COUNT(DISTINCT product) from zt_object where project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) into objects__DELIMITER__
- IF products = objects THEN
- return 1__DELIMITER__
- ELSEIF products != objects THEN
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_initscale`;
-CREATE FUNCTION qc_initscale($project int, $category varchar(30), $estimateType varchar(30)) RETURNS float(10,2)
-BEGIN
- declare $estimate int default 0__DELIMITER__
- declare $storyEst varchar(30) default 'storyEst'__DELIMITER__
- declare $requestEst varchar(30) default 'requestEst'__DELIMITER__
- if($estimateType = $storyEst) THEN SELECT sum(storyEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
- end if__DELIMITER__
- if($estimateType = $requestEst) THEN SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
- end if__DELIMITER__
- RETURN @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmplanscale`;
-CREATE FUNCTION `qc_pgmplanscale`($project int) RETURNS float(10,2)
-BEGIN
- declare programScale float (10,2) default 0__DELIMITER__
- select `scale` from zt_workestimation where project = $project into @programScale__DELIMITER__
- return @programScale__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmsrinitscale`;
-CREATE FUNCTION `qc_pgmsrinitscale`($project int) RETURNS float(10,2)
-begin
- declare scale int default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project, 'SRS') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_initscale($project, 'SRS', 'storyEst') into scale __DELIMITER__
- return scale __DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmsrrealscale`;
-CREATE FUNCTION `qc_pgmsrrealscale`($project int) RETURNS float(10,2)
-BEGIN
- declare totalEstimate float(10,2) default 0__DELIMITER__
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where id in (select story from zt_projectstory where project=$project) and type='story' and deleted='0' and closedReason not in ('subdivided', 'duplicate', 'willnotdo', 'cancel', 'bydesign') into totalEstimate__DELIMITER__
- return totalEstimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmurinitscale`;
-CREATE FUNCTION `qc_pgmurinitscale`($project int) RETURNS float(10,2)
-begin
- declare scale int default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project, 'URS') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_initscale($project, 'URS', 'requestEst') into scale__DELIMITER__
- return scale__DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmurrealscale`;
-CREATE FUNCTION `qc_pgmurrealscale`($project int) RETURNS float(10,2)
-BEGIN
- declare totalEstimate float(10,2) default 0__DELIMITER__
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where project=$project and type='requirement' and deleted='0' and closedReason not in ('subdivided', 'duplicate', 'willnotdo', 'cancel', 'bydesign') into totalEstimate__DELIMITER__
- return totalEstimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmallrequirementstage`;
-CREATE FUNCTION `qc_pgmallrequirementstage`($project int) RETURNS int(1)
-BEGIN
- -- 获取项目产品总数
- select COUNT(1) AS products from zt_projectproduct where project = $project into @totalproduct__DELIMITER__
- -- 获取已经设置需求阶段的产品总数
- select COUNT(1) AS product from (select product from zt_projectproduct where project in (select id from zt_project where project = $project and type = 'stage' and attribute = 'request' and deleted = '0') GROUP BY product) as product into @product__DELIMITER__
- -- 让项目产品总数和已设置需求阶段产品总数比较,都设置返回1,否则返回0
- if @totalproduct = @product then return 1__DELIMITER__
- end if__DELIMITER__
- RETURN 0__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesigntplandays`;
-CREATE FUNCTION `qc_pgmdesigntplandays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesigntrealdays`;
-CREATE FUNCTION `qc_pgmdesigntrealdays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelplandays`;
-CREATE FUNCTION `qc_pgmdevelplandays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealdays`;
-CREATE FUNCTION `qc_pgmdevelrealdays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestplandays`;
-CREATE FUNCTION `qc_pgmrequestplandays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealdays`;
-CREATE FUNCTION `qc_pgmrequestrealdays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmspecifiedtypeactualdays`;
-CREATE FUNCTION `qc_pgmspecifiedtypeactualdays`($project int,$attribute varchar(50)) RETURNS int(10)
-BEGIN
- -- 查询某类型的阶段总数
- select COUNT(1) from zt_project where project = $project and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @totalstory__DELIMITER__
- -- 查询某类型已设置实际工期的阶段总数
- select COUNT(1) from zt_project where project = $project and attribute = $attribute and deleted = '0' and realDuration > 0 and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @setstory__DELIMITER__
- -- 查询项目下某类型阶段实际工期总数
- select sum(realDuration) as realDuration from zt_project where project = $project and attribute = $attribute and deleted = '0' and realDuration > 0 and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @days__DELIMITER__
- -- 判断项目下某类型的阶段是否都已设置实际工期
- if @totalstory != @setstory then
- set @days = 0__DELIMITER__
- end if__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmspecifiedtypeplanneddays`;
-CREATE FUNCTION `qc_pgmspecifiedtypeplanneddays`($project int,$attribute varchar(50)) RETURNS int(10)
-BEGIN
- select sum(planDuration) as planDuration from zt_project where project = $project and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmstageactualduration`;
-CREATE FUNCTION `qc_pgmstageactualduration`($product int, $attribute varchar(50)) RETURNS int(10)
-BEGIN
- -- 查找某类型的阶段总数
- select COUNT(1) as totalduration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) into @totalduration__DELIMITER__
- -- 查某类型阶段已设置实际工期的总数
- select COUNT(1) as setduration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and realDuration > 0 into @setduration__DELIMITER__
- -- 指定产品下某类型的阶段实际工期总和
- select sum(realDuration) as duration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and realDuration > 0 into @duration__DELIMITER__
- -- 需要判断该类型阶段都已设置实际工期,否则不统计
- if @totalduration != @setduration then
- set @duration = 0__DELIMITER__
- end if__DELIMITER__
- return @duration__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmstageplannedduration`;
-CREATE FUNCTION `qc_pgmstageplannedduration`($product int, $attribute varchar(50)) RETURNS int(10)
-BEGIN
- -- 查找某产品对应阶段
- select sum(planDuration) as duration from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and planDuration > 0 into @duration__DELIMITER__
- RETURN @duration__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestplandays`;
-CREATE FUNCTION `qc_pgmtestplandays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealdays`;
-CREATE FUNCTION `qc_pgmtestrealdays`($project int) RETURNS int(10)
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddesigntplandays`;
-CREATE FUNCTION `qc_prddesigntplandays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddesigntrealdays`;
-CREATE FUNCTION `qc_prddesigntrealdays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddevelplandays`;
-CREATE FUNCTION `qc_prddevelplandays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddevelrealdays`;
-CREATE FUNCTION `qc_prddevelrealdays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdrequestplandays`;
-CREATE FUNCTION `qc_prdrequestplandays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdrequestrealdays`;
-CREATE FUNCTION `qc_prdrequestrealdays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdtestplandays`;
-CREATE FUNCTION `qc_prdtestplandays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdtestrealdays`;
-CREATE FUNCTION `qc_prdtestrealdays`($project int, $product int) RETURNS int(10)
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesgignrealesthours`;
-CREATE FUNCTION `qc_pgmdesgignrealesthours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmesthoursbytype($project, 'design')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesignrealhours`;
-CREATE FUNCTION `qc_pgmdesignrealhours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmrealhoursbytype($project, 'design')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealesthours`;
-CREATE FUNCTION `qc_pgmdevelrealesthours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmesthoursbytype($project, 'devel')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealhours`;
-CREATE FUNCTION `qc_pgmdevelrealhours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmrealhoursbytype($project, 'devel')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealesthours`;
-CREATE FUNCTION `qc_pgmrealesthours`($project int) RETURNS float(10,2)
-BEGIN
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_task where project=$project and parent >= 0 and status != 'cancel' and deleted = '0' into @estimate__DELIMITER__
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmesthoursbytype`;
-CREATE FUNCTION `qc_pgmesthoursbytype`($project int, $type char(30)) RETURNS float(10,2)
-BEGIN
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_task where project=$project and type = $type and parent >= 0 and status != 'cancel' and deleted = '0' into @estimate__DELIMITER__
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealhours`;
-CREATE FUNCTION `qc_pgmrealhours`($project int) RETURNS float(10,2)
-BEGIN
- select CAST(sum(consumed) as DECIMAL(10,2)) as consumed from zt_task where project=$project and parent >= 0 and status != 'cancel' and deleted = '0' into @consumed__DELIMITER__
- return @consumed__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealhoursbytype`;
-CREATE FUNCTION `qc_pgmrealhoursbytype`($project int, $type char(30)) RETURNS float(10,2)
-BEGIN
- select CAST(sum(consumed) as DECIMAL(10,2)) as consumed from zt_task where project=$project and type = $type and parent >= 0 and status != 'cancel' and deleted = '0' into @consumed__DELIMITER__
- return @consumed__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealesthours`;
-CREATE FUNCTION `qc_pgmrequestrealesthours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmesthoursbytype($project, 'request')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealhours`;
-CREATE FUNCTION `qc_pgmrequestrealhours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmrealhoursbytype($project, 'request')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealesthours`;
-CREATE FUNCTION `qc_pgmtestrealesthours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmesthoursbytype($project, 'test')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealhours`;
-CREATE FUNCTION `qc_pgmtestrealhours`($project int) RETURNS float(10,2)
-BEGIN
-return qc_pgmrealhoursbytype($project, 'test')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdevelfirstesthours`;
-CREATE FUNCTION `qc_getdevelfirstesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(devEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdesignfirstesthours`;
-CREATE FUNCTION `qc_getdesignfirstesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(designEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getstoryfirstesthours`;
-CREATE FUNCTION `qc_getstoryfirstesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_gettestfirstesthours`;
-CREATE FUNCTION `qc_gettestfirstesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(testEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getfirstesthours`;
-CREATE FUNCTION `qc_getfirstesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(taskEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdevlastesthours`;
-CREATE FUNCTION `qc_getdevlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(devEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getrequestlastesthours`;
-CREATE FUNCTION `qc_getrequestlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_gettestlastesthours`;
-CREATE FUNCTION `qc_gettestlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(testEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdesignlastesthours`;
-CREATE FUNCTION `qc_getdesignlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(designEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getlastesthours`;
-CREATE FUNCTION `qc_getlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- SELECT sum(taskEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmlastesthours`;
-CREATE FUNCTION `qc_pgmlastesthours`($project int) RETURNS float(10,2)
-BEGIN
- declare estimate float(10,2) default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project,'PP') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_getlastesthours($project) into estimate__DELIMITER__
- return estimate__DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
diff --git a/db/zentao.sql b/db/zentao.sql
index 40d0354534..0e216c43a3 100755
--- a/db/zentao.sql
+++ b/db/zentao.sql
@@ -1285,6 +1285,7 @@ CREATE TABLE IF NOT EXISTS `zt_oauth` (
CREATE INDEX `account` ON `zt_oauth` (`account`);
CREATE INDEX `providerType` ON `zt_oauth` (`providerType`);
CREATE INDEX `providerID` ON `zt_oauth` (`providerID`);
+CREATE UNIQUE INDEX `account_openID` ON `zt_oauth`(`account`,`openID`,`providerType`,`providerID`);
-- DROP TABLE IF EXISTS `zt_pipeline`;
CREATE TABLE IF NOT EXISTS `zt_pipeline` (
@@ -3364,7 +3365,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(1, 'bug', 'batchResolve'),
(1, 'bug', 'browse'),
(1, 'bug', 'close'),
-(1, 'bug', 'confirmBug'),
+(1, 'bug', 'confirm'),
(1, 'bug', 'confirmStoryChange'),
(1, 'bug', 'create'),
(1, 'bug', 'delete'),
@@ -4797,7 +4798,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(2, 'bug', 'batchResolve'),
(2, 'bug', 'browse'),
(2, 'bug', 'close'),
-(2, 'bug', 'confirmBug'),
+(2, 'bug', 'confirm'),
(2, 'bug', 'confirmStoryChange'),
(2, 'bug', 'create'),
(2, 'bug', 'delete'),
@@ -5582,7 +5583,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(3, 'bug', 'batchResolve'),
(3, 'bug', 'browse'),
(3, 'bug', 'close'),
-(3, 'bug', 'confirmBug'),
+(3, 'bug', 'confirm'),
(3, 'bug', 'confirmStoryChange'),
(3, 'bug', 'create'),
(3, 'bug', 'delete'),
@@ -6225,7 +6226,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(4, 'bug', 'batchResolve'),
(4, 'bug', 'browse'),
(4, 'bug', 'close'),
-(4, 'bug', 'confirmBug'),
+(4, 'bug', 'confirm'),
(4, 'bug', 'confirmStoryChange'),
(4, 'bug', 'create'),
(4, 'bug', 'delete'),
@@ -7297,7 +7298,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(5, 'bug', 'batchResolve'),
(5, 'bug', 'browse'),
(5, 'bug', 'close'),
-(5, 'bug', 'confirmBug'),
+(5, 'bug', 'confirm'),
(5, 'bug', 'confirmStoryChange'),
(5, 'bug', 'create'),
(5, 'bug', 'delete'),
@@ -8236,7 +8237,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(6, 'bug', 'batchResolve'),
(6, 'bug', 'browse'),
(6, 'bug', 'close'),
-(6, 'bug', 'confirmBug'),
+(6, 'bug', 'confirm'),
(6, 'bug', 'confirmStoryChange'),
(6, 'bug', 'create'),
(6, 'bug', 'delete'),
@@ -9047,7 +9048,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(7, 'bug', 'batchResolve'),
(7, 'bug', 'browse'),
(7, 'bug', 'close'),
-(7, 'bug', 'confirmBug'),
+(7, 'bug', 'confirm'),
(7, 'bug', 'confirmStoryChange'),
(7, 'bug', 'create'),
(7, 'bug', 'delete'),
@@ -9877,7 +9878,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(8, 'bug', 'batchResolve'),
(8, 'bug', 'browse'),
(8, 'bug', 'close'),
-(8, 'bug', 'confirmBug'),
+(8, 'bug', 'confirm'),
(8, 'bug', 'confirmStoryChange'),
(8, 'bug', 'create'),
(8, 'bug', 'delete'),
@@ -10736,7 +10737,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(9, 'bug', 'batchResolve'),
(9, 'bug', 'browse'),
(9, 'bug', 'close'),
-(9, 'bug', 'confirmBug'),
+(9, 'bug', 'confirm'),
(9, 'bug', 'confirmStoryChange'),
(9, 'bug', 'create'),
(9, 'bug', 'delete'),
@@ -11449,7 +11450,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(10, 'bug', 'batchResolve'),
(10, 'bug', 'browse'),
(10, 'bug', 'close'),
-(10, 'bug', 'confirmBug'),
+(10, 'bug', 'confirm'),
(10, 'bug', 'confirmStoryChange'),
(10, 'bug', 'create'),
(10, 'bug', 'edit'),
@@ -11962,7 +11963,7 @@ REPLACE INTO `zt_grouppriv` (`group`, `module`, `method`) VALUES
(11, 'bug', 'batchResolve'),
(11, 'bug', 'browse'),
(11, 'bug', 'close'),
-(11, 'bug', 'confirmBug'),
+(11, 'bug', 'confirm'),
(11, 'bug', 'confirmStoryChange'),
(11, 'bug', 'create'),
(11, 'bug', 'edit'),
@@ -15378,49 +15379,6 @@ REPLACE INTO `zt_zoutput` (`id`, `activity`, `name`, `content`, `optional`, `tai
(493, 328, '项目度量数据库', '', 'yes', '', '', 'admin', '2020-01-09 14:55:08', '', NULL, 615, '0'),
(494, 329, '《量化项目计划及跟踪表》', '', 'no', '', '', 'admin', '2020-01-09 14:59:04', '', NULL, 630, '0');
-REPLACE INTO `zt_basicmeas` (`id`, `purpose`, `scope`, `object`, `name`, `code`, `unit`, `configure`, `params`, `definition`, `source`, `collectType`, `collectConf`, `execTime`, `collectedBy`, `createdBy`, `createdDate`, `editedBy`, `editedDate`, `order`, `deleted`) VALUES
-(2,'scale','project','userRequest','项目用户需求初始规模','pgmURInitScale','故事点或功能点','CREATE FUNCTION qc_pgmurinitscale($project int) returns float (10,2)\r\nbegin\r\n declare scale float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'URS\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_initscale($project, \'URS\',\'requestEst\') into scale__DELIMITER__\r\n return scale__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nend','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目每个产品的第一个用户需求规格说明书基线版本的规模之和','从基线表中查询该项目下面每个产品的第一个用户需求规模说明书版本,然后查询对应的需求,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 14:19:41',10,'0'),
-(3,'scale','project','softRequest','项目软件需求初始规模','pgmSRInitScale','故事点或功能点','CREATE FUNCTION qc_pgmsrinitscale($project int) returns float (10,2)\r\nbegin\r\n declare scale float (10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'SRS\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_initscale($project, \'SRS\',\'storyEst\') into scale __DELIMITER__\r\n return scale __DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nend','{\"$project\":{\"showName\":\"\\u6240\\u9700\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目每个产品的第一个软件需求规格说明书基线版本的规模之和','从基线表中查询该项目下面每个产品的第一个软件需求规模说明书版本,然后查询对应的需求,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 14:21:53',15,'0'),
-(4,'scale','project','userRequest','项目用户需求实时规模','pgmURRealScale','故事点或功能点','CREATE FUNCTION `qc_pgmurrealscale`($project int) RETURNS float (10,2)\r\nBEGIN\r\n declare totalEstimate float(10,2) default 0__DELIMITER__\r\n select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where project=$project and type=\'requirement\' and deleted=\'0\' and closedReason not in (\'subdivided\', \'duplicate\', \'willnotdo\', \'cancel\', \'bydesign\') into totalEstimate__DELIMITER__\r\n return totalEstimate__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目用户需求实际的规模','从需求表中查询该项目下的所有用户需求,对规模进行求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 14:22:17',20,'0'),
-(5,'scale','project','softRequest','项目软件需求实时规模','pgmSRRealScale','故事点或功能点','CREATE FUNCTION `qc_pgmsrrealscale`($project int) RETURNS float (10,2)\r\nBEGIN\r\n declare totalEstimate float (10,2) default 0__DELIMITER__\r\n select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where id in (select story from zt_projectstory where project=$project) and type=\'story\' and deleted=\'0\' and closedReason not in (\'subdivided\', \'duplicate\', \'willnotdo\', \'cancel\', \'bydesign\') into totalEstimate__DELIMITER__\r\n return totalEstimate__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":false,\"options\":\"project\",\"defaultValue\":\"702\"}}','项目软件需求实际的规模','从需求表中查询该项目下的所有软件需求,对规模进行求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 14:28:01',25,'0'),
-(6,'scale','project','program','项目估算规模','pgmPlanScale','故事点或功能点','CREATE FUNCTION `qc_pgmplanscale`($project int) RETURNS float (10,2)\r\nBEGIN\r\n declare programScale float (10,2) default 0__DELIMITER__\r\n select `scale` from zt_workestimation where project = $project into programScale__DELIMITER__\r\n return programScale__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目最初估算时估计的规模','从项目估算表里面查询项目的估算规模。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 14:26:01',30,'0'),
-(8,'duration','project','stage','项目需求阶段计划天数','pgmRequestPlanDays','天','CREATE FUNCTION `qc_pgmrequestplandays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeplanneddays($project,\'request\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有需求阶段计划天数的和','从阶段表里面统计该项目下面所有类型为需求的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',40,'0'),
-(9,'duration','project','stage','项目设计阶段计划天数','pgmDesigntPlanDays','天','CREATE FUNCTION `qc_pgmdesigntplandays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeplanneddays($project,\'design\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有设计阶段计划天数的和','从阶段表里面统计该项目下面所有类型为设计的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',45,'0'),
-(10,'duration','project','stage','项目开发阶段计划天数','pgmDevelPlanDays','天','CREATE FUNCTION `qc_pgmdevelplandays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeplanneddays($project,\'dev\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有研发阶段计划天数的和','从阶段表里面统计该项目下面所有类型为开发的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',50,'0'),
-(11,'duration','project','stage','项目测试阶段计划天数','pgmTestPlanDays','天','CREATE FUNCTION `qc_pgmtestplandays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeplanneddays($project,\'qa\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有测试阶段计划天数的和','从阶段表里面统计该项目下面所有类型为测试的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',55,'0'),
-(12,'duration','project','stage','项目需求阶段实际天数','pgmRequestRealDays','天','CREATE FUNCTION `qc_pgmrequestrealdays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeactualdays($project,\'request\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有需求阶段实际天数的和','从阶段表里面统计该项目下面所有类型为需求的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',60,'0'),
-(13,'duration','project','stage','项目设计阶段实际天数','pgmDesigntRealDays','天','CREATE FUNCTION `qc_pgmdesigntrealdays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeactualdays($project,\'design\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有设计阶段实际天数的和','从阶段表里面统计该项目下面所有类型为设计的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',65,'0'),
-(14,'duration','project','stage','项目开发阶段实际天数','pgmDevelRealDays','天','CREATE FUNCTION `qc_pgmdevelrealdays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeactualdays($project,\'dev\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有研发阶段实际天数的和','从阶段表里面统计该项目下面所有类型为开发的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',70,'0'),
-(15,'duration','project','stage','项目测试阶段实际天数','pgmTestRealDays','天','CREATE FUNCTION `qc_pgmtestrealdays`($project int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmspecifiedtypeactualdays($project,\'qa\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"3\"}}','项目下面所有测试阶段实际天数的和','从阶段表里面统计该项目下面所有类型为测试的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',75,'0'),
-(26,'duration','product','stage','分产品需求阶段计划天数','prdRequestPlanDays','天','CREATE FUNCTION `qc_prdrequestplandays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageplannedduration($product, \'request\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有需求阶段计划天数的和','从阶段表里面统计该产品在该项目下所有类型为需求的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',130,'0'),
-(27,'duration','product','stage','分产品设计阶段计划天数','prdDesigntPlanDays','天','CREATE FUNCTION `qc_prddesigntplandays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageplannedduration($product, \'design\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有设计阶段计划天数的和','从阶段表里面统计该产品在该项目下所有类型为设计的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',135,'0'),
-(28,'duration','product','stage','分产品开发阶段计划天数','prdDevelPlanDays','天','CREATE FUNCTION `qc_prddevelplandays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageplannedduration($product, \'dev\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"1\"}}','产品下面所有研发阶段计划天数的和','从阶段表里面统计该产品在该项目下所有类型为开发的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',140,'0'),
-(29,'duration','product','stage','分产品测试阶段计划天数','prdTestPlanDays','天','CREATE FUNCTION `qc_prdtestplandays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageplannedduration($product, \'qa\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有测试阶段计划天数的和','从阶段表里面统计该产品在该项目下所有类型为测试的阶段的计划天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',145,'0'),
-(30,'duration','product','stage','分产品需求阶段实际天数','prdRequestRealDays','天','CREATE FUNCTION `qc_prdrequestrealdays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageactualduration($product,\'request\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有需求阶段实际天数的和','从阶段表里面统计该产品在该项目下所有类型为需求的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',150,'0'),
-(31,'duration','product','stage','分产品设计阶段实际天数','prdDesigntRealDays','天','CREATE FUNCTION `qc_prddesigntrealdays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageactualduration($product, \'design\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有设计阶段实际天数的和','从阶段表里面统计该产品在该项目下所有类型为设计的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',155,'0'),
-(32,'duration','product','stage','分产品开发阶段实际天数','prdDevelRealDays','天','CREATE FUNCTION `qc_prddevelrealdays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageactualduration($product, \'dev\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"\"}}','产品下面所有研发阶段实际天数的和','从阶段表里面统计该产品在该项目下所有类型为开发的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',160,'0'),
-(33,'duration','product','stage','分产品测试阶段实际天数','prdTestRealDays','天','CREATE FUNCTION `qc_prdtestrealdays`($product int) RETURNS int(11)\r\nBEGIN\r\n select qc_pgmstageactualduration($product, \'qa\') as days into @days__DELIMITER__\r\n return @days__DELIMITER__\r\nEND','{\"$product\":{\"showName\":\"\\u6240\\u5c5e\\u4ea7\\u54c1\",\"varName\":\"$product\",\"varType\":\"select\",\"options\":\"product\",\"defaultValue\":\"1\"}}','产品下面所有测试阶段实际天数的和','从阶段表里面统计该产品在该项目下所有类型为测试的阶段的实际天数,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','','1970-01-01 00:00:01',165,'0'),
-(34,'workload','project','finance','项目任务实时预计工时数','pgmRealEstHours','小时','CREATE FUNCTION `qc_pgmrealesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n select sum(estimate) from zt_task where project=$project and parent >= 0 and status != \'cancel\' and deleted = \'0\' into @estimate__DELIMITER__\r\nreturn @estimate__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有任务的最初预计工时和','从任务表中查询该项目的所有任务,统计最初预计工>时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 19:51:39',170,'0'),
-(35,'workload','project','finance','项目需求工作实时总预计工时数','pgmRequestRealEstHours','小时','CREATE FUNCTION `qc_pgmrequestrealesthours`($project int) RETURNS float (10,2)\r\nBEGIN\r\nreturn qc_pgmesthoursbytype($project, \'request\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有需求相关任务的最初预计工时和','从任务表中查询该项目所有任务类型为需求的任务,统计最初预计工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-23 13:49:17',175,'0'),
-(36,'workload','project','finance','项目设计工作实时总预计工时数','pgmDesgignRealEstHours','小时','CREATE FUNCTION `qc_pgmdesgignrealesthours`($project int) RETURNS float (10,2)\r\nBEGIN\r\nreturn qc_pgmesthoursbytype($project, \'design\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有设计相关任务的最初预计工时和','从任务表中查询该项目所有任务类型为设计的任务,统计最初预计工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-23 13:45:32',180,'0'),
-(37,'workload','project','finance','项目开发工作实时总预计工时数','pgmDevelRealEstHours','小时','CREATE FUNCTION `qc_pgmdevelrealesthours`($project int) RETURNS float (10,2)\r\nBEGIN\r\nreturn qc_pgmesthoursbytype($project, \'devel\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有开发相关任务的最初预计工时和','从任务表中查询该项目所有任务类型为开发的任务,统计最初预计工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-23 13:46:53',185,'0'),
-(38,'workload','project','finance','项目测试工作实时总预计工时数','pgmTestRealEstHours','小时','CREATE FUNCTION `qc_pgmtestrealesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\nreturn qc_pgmesthoursbytype($project, \'test\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有测试相关任务的最初预计工时和','从任务表中查询该项目所有任务类型为测试的任务,统计最初预计工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-23 13:44:13',190,'0'),
-(39,'workload','project','finance','项目任务实际消耗工时数','pgmRealHours','小时','CREATE FUNCTION `qc_pgmrealhours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n select CAST(sum(consumed) as DECIMAL(10,2)) as consumed from zt_task where project=$project and parent >= 0 and status != \'cancel\' and deleted = \'0\' into @consumed__DELIMITER__\r\n return @consumed__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目下面所有任务的实际消耗工时和','从任务表中查询该项目的所有任务,统计实际消耗工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 19:49:32',195,'0'),
-(40,'workload','project','finance','项目需求工作实际消耗工时数','pgmRequestRealHours','小时','CREATE FUNCTION `qc_pgmrequestrealhours`($project int) RETURNS float(10,2)\r\nBEGIN\r\nreturn qc_pgmrealhoursbytype($project, \'request\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有需求相关任务的实际消耗工时和','从任务表中查询该项目所有任务类型为需求的任务,统计实际消耗工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 19:49:03',200,'0'),
-(41,'workload','project','finance','项目设计工作实际消耗工时数','pgmDesignRealHours','小时','CREATE FUNCTION `qc_pgmdesignrealhours`($project int) RETURNS float(10,2)\r\nBEGIN\r\nreturn qc_pgmrealhoursbytype($project, \'design\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有设计相关任务的实际消耗工时和','从任务表中查询该项目所有任务类型为设计的任务,统计实际消耗工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 19:48:35',205,'0'),
-(42,'workload','project','finance','项目开发工作实际消耗工时数','pgmDevelRealHours','小时','CREATE FUNCTION `qc_pgmdevelrealhours`($project int) RETURNS float(10,2)\r\nBEGIN\r\nreturn qc_pgmrealhoursbytype($project, \'devel\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有开发相关任务的实际消耗工时和','从任务表中查询该项目所有任务类型为开发的任务,统计实际消耗工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 18:34:51',210,'0'),
-(43,'workload','project','finance','项目测试工作实际消耗工时数','pgmTestRealHours','小时','CREATE FUNCTION `qc_pgmtestrealhours`($project int) RETURNS float(10, 2)\r\nBEGIN\r\nreturn qc_pgmrealhoursbytype($project, \'test\')__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目所有测试相关任务的实际消耗工时和','从任务表中查询该项目所有任务类型为测试的任务,统计实际消耗工时,求和。','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','system','1970-01-01 00:00:01','admin','2020-07-07 18:09:01',215,'0'),
-(44,'workload','project','finance','项目开发工作最初总预计工时数','pgmDevelFirstEstHours','小时','CREATE FUNCTION `qc_pgmdevelfirstesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getdevelfirstesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划第一个基线版本中所有开发相关工作最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-22 13:13:51','','1970-01-01 00:00:01',220,'0'),
-(45,'workload','project','finance','项目设计工作最初总预计工时数','pgmDesignFirstEstHours','小时','CREATE FUNCTION `qc_pgmdesignfirstesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getdesignfirstesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划第一个基线版本中所有设计相关工作最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-22 16:33:20','admin','2020-07-23 10:31:23',225,'0'),
-(46,'workload','project','finance','项目测试工作最初总预计工时数','pgmTestFirstEstHours','小时','CREATE FUNCTION `qc_pgmtestfirstesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_gettestfirstesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划第一个基线版本中所有测试相关工作最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 10:31:17','','1970-01-01 00:00:01',230,'0'),
-(47,'workload','project','finance','项目需求工作最初总预计工时数','pgmRequestFirstEstHours','小时','CREATE FUNCTION `qc_pgmrequestfirstesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getstoryfirstesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划第一个基线版本中所有需求相关工作最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 10:53:09','','1970-01-01 00:00:01',235,'0'),
-(48,'workload','project','finance','项目任务最初总预计工时数','pgmFirstEstHours','小时','CREATE FUNCTION `qc_pgmfirstesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getfirstesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划第一个基线版本中所有任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 13:06:59','','1970-01-01 00:00:01',240,'0'),
-(49,'workload','project','finance','项目开发工作最终总预计工时数','pgmDevelLastEstHours','小时','CREATE FUNCTION `qc_pgmdevellastesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project, \'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getdevlastesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划最后一个基线版本中所有开发相关任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 13:41:38','','1970-01-01 00:00:01',245,'0'),
-(50,'workload','project','finance','项目需求工作最终总预计工时数','pgmRequestLastEstHours','小时','CREATE FUNCTION `qc_pgmrequestlastesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project,\'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getrequestlastesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划最后一个基线版本中所有需求相关任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 14:00:58','','1970-01-01 00:00:01',250,'0'),
-(51,'workload','project','finance','项目测试工作最终总预计工时数','pgmTestLastEstHours','小时','CREATE FUNCTION `qc_pgmtestlastesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project,\'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_gettestlastesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划最后一个基线版本中所有测试相关任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 14:10:12','','1970-01-01 00:00:01',255,'0'),
-(52,'workload','project','finance','项目设计工作最终总预计工时数','pgmDesignLastEstHours','小时','CREATE FUNCTION `qc_pgmdesignlastesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project,\'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getdesignlastesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划最后一个基线版本中所有设计相关任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 14:33:00','','1970-01-01 00:00:01',260,'0'),
-(53,'workload','project','finance','项目任务最终总预计工时数','pgmLastEstHours','小时','CREATE FUNCTION `qc_pgmlastesthours`($project int) RETURNS float(10,2)\r\nBEGIN\r\n declare estimate float(10,2) default 0__DELIMITER__\r\n declare inited int default 0__DELIMITER__\r\n select qc_cminited($project,\'PP\') into inited__DELIMITER__\r\n IF inited = 1 THEN\r\n select qc_getlastesthours($project) into estimate__DELIMITER__\r\n return estimate__DELIMITER__\r\n ELSE \r\n return 0__DELIMITER__\r\n END IF__DELIMITER__\r\nEND','{\"$project\":{\"showName\":\"\\u6240\\u5c5e\\u9879\\u76ee\",\"varName\":\"$project\",\"varType\":\"select\",\"options\":\"project\",\"defaultValue\":\"\"}}','项目计划最后一个基线版本中所有任务最初预计工时和','','crontab','{\"week\":\"1,2,3,4,5,6,0\",\"type\":\"week\"}','00:00','','admin','2020-07-23 14:54:42','','1970-01-01 00:00:01',265,'0');
-
REPLACE INTO `zt_cron` (`m`, `h`, `dom`, `mon`, `dow`, `command`, `remark`, `type`, `buildin`, `status`) VALUES
('1','0','*','*','*','moduleName=weekly&methodName=computeWeekly','更新项目周报','zentao',0,'normal');
@@ -15641,442 +15599,6 @@ CREATE TABLE IF NOT EXISTS `zt_solution` (
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
-DROP FUNCTION IF EXISTS `get_monday`;
-CREATE FUNCTION `get_monday`(day date) RETURNS date READS SQL DATA
- begin if date_format(day, '%w') = 0 then return subdate(day, date_format(day, '%w') - 6)__DELIMITER__
- else return subdate(day, date_format(day, '%w') -1)__DELIMITER__
- end if__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `get_sunday`;
-CREATE FUNCTION `get_sunday`(day date) RETURNS date READS SQL DATA
-begin
- if date_format(day, '%w') = 0 then return day__DELIMITER__
- else return subdate(day, date_format(day, '%w') - 7)__DELIMITER__
- end if__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_cminited`;
-CREATE FUNCTION qc_cminited($project int, $category varchar(30)) returns int READS SQL DATA
-begin
- declare products int default 0__DELIMITER__
- declare objects int default 0__DELIMITER__
- select COUNT(1) from zt_projectproduct where project = $project into products__DELIMITER__
- select COUNT(DISTINCT product) from zt_object where project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) into objects__DELIMITER__
- IF products = objects THEN
- return 1__DELIMITER__
- ELSEIF products != objects THEN
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_initscale`;
-CREATE FUNCTION qc_initscale($project int, $category varchar(30), $estimateType varchar(30)) RETURNS float(10,2) READS SQL DATA
-BEGIN
- declare $estimate int default 0__DELIMITER__
- declare $storyEst varchar(30) default 'storyEst'__DELIMITER__
- declare $requestEst varchar(30) default 'requestEst'__DELIMITER__
- if($estimateType = $storyEst) THEN SELECT sum(storyEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
- end if__DELIMITER__
- if($estimateType = $requestEst) THEN SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = $category and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
- end if__DELIMITER__
- RETURN @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmplanscale`;
-CREATE FUNCTION `qc_pgmplanscale`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- declare programScale float (10,2) default 0__DELIMITER__
- select `scale` from zt_workestimation where project = $project into @programScale__DELIMITER__
- return @programScale__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmsrinitscale`;
-CREATE FUNCTION `qc_pgmsrinitscale`($project int) RETURNS float(10,2) READS SQL DATA
-begin
- declare scale int default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project, 'SRS') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_initscale($project, 'SRS', 'storyEst') into scale __DELIMITER__
- return scale __DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmsrrealscale`;
-CREATE FUNCTION `qc_pgmsrrealscale`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- declare totalEstimate float(10,2) default 0__DELIMITER__
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where id in (select story from zt_projectstory where project=$project) and type='story' and deleted='0' and closedReason not in ('subdivided', 'duplicate', 'willnotdo', 'cancel', 'bydesign') into totalEstimate__DELIMITER__
- return totalEstimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmurinitscale`;
-CREATE FUNCTION `qc_pgmurinitscale`($project int) RETURNS float(10,2) READS SQL DATA
-begin
- declare scale int default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project, 'URS') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_initscale($project, 'URS', 'requestEst') into scale__DELIMITER__
- return scale__DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmurrealscale`;
-CREATE FUNCTION `qc_pgmurrealscale`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- declare totalEstimate float(10,2) default 0__DELIMITER__
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_story where project=$project and type='requirement' and deleted='0' and closedReason not in ('subdivided', 'duplicate', 'willnotdo', 'cancel', 'bydesign') into totalEstimate__DELIMITER__
- return totalEstimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmallrequirementstage`;
-CREATE FUNCTION `qc_pgmallrequirementstage`($project int) RETURNS int(1) READS SQL DATA
-BEGIN
- -- 获取项目产品总数
- select COUNT(1) AS products from zt_projectproduct where project = $project into @totalproduct__DELIMITER__
- -- 获取已经设置需求阶段的产品总数
- select COUNT(1) AS product from (select product from zt_projectproduct where project in (select id from zt_project where project = $project and type = 'stage' and attribute = 'request' and deleted = '0') GROUP BY product) as product into @product__DELIMITER__
- -- 让项目产品总数和已设置需求阶段产品总数比较,都设置返回1,否则返回0
- if @totalproduct = @product then return 1__DELIMITER__
- end if__DELIMITER__
- RETURN 0__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesigntplandays`;
-CREATE FUNCTION `qc_pgmdesigntplandays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesigntrealdays`;
-CREATE FUNCTION `qc_pgmdesigntrealdays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelplandays`;
-CREATE FUNCTION `qc_pgmdevelplandays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealdays`;
-CREATE FUNCTION `qc_pgmdevelrealdays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestplandays`;
-CREATE FUNCTION `qc_pgmrequestplandays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealdays`;
-CREATE FUNCTION `qc_pgmrequestrealdays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmspecifiedtypeactualdays`;
-CREATE FUNCTION `qc_pgmspecifiedtypeactualdays`($project int,$attribute varchar(50)) RETURNS int(11) READS SQL DATA
-BEGIN
- -- 查询某类型的阶段总数
- select COUNT(1) from zt_project where project = $project and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @totalstory__DELIMITER__
- -- 查询某类型已设置实际工期的阶段总数
- select COUNT(1) from zt_project where project = $project and attribute = $attribute and deleted = '0' and realDuration > 0 and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @setstory__DELIMITER__
- -- 查询项目下某类型阶段实际工期总数
- select sum(realDuration) as realDuration from zt_project where project = $project and attribute = $attribute and deleted = '0' and realDuration > 0 and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @days__DELIMITER__
- -- 判断项目下某类型的阶段是否都已设置实际工期
- if @totalstory != @setstory then
- set @days = 0__DELIMITER__
- end if__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmspecifiedtypeplanneddays`;
-CREATE FUNCTION `qc_pgmspecifiedtypeplanneddays`($project int,$attribute varchar(50)) RETURNS int(11) READS SQL DATA
-BEGIN
- select sum(planDuration) as planDuration from zt_project where project = $project and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where project = $project and attribute = $attribute and grade = 2 group by parent) into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmstageactualduration`;
-CREATE FUNCTION `qc_pgmstageactualduration`($product int, $attribute varchar(50)) RETURNS int(11) READS SQL DATA
-BEGIN
- -- 查找某类型的阶段总数
- select COUNT(1) AS totalduration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) into @totalduration__DELIMITER__
- -- 查某类型阶段已设置实际工期的总数
- select COUNT(1) AS setduration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and realDuration > 0 into @setduration__DELIMITER__
- -- 指定产品下某类型的阶段实际工期总和
- select sum(realDuration) as duration from zt_project where id in (select project from zt_projectproduct where product = $product) and type = 'stage' and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and realDuration > 0 into @duration__DELIMITER__
- -- 需要判断该类型阶段都已设置实际工期,否则不统计
- if @totalduration != @setduration then
- set @duration = 0__DELIMITER__
- end if__DELIMITER__
- return @duration__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmstageplannedduration`;
-CREATE FUNCTION `qc_pgmstageplannedduration`($product int, $attribute varchar(50)) RETURNS int(11) READS SQL DATA
-BEGIN
- -- 查找某产品对应阶段
- select sum(planDuration) as duration from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and deleted = '0' and id not in (select parent from zt_project where id in (select project from zt_projectproduct where product = $product) and attribute = $attribute and grade = 2 group by parent) and planDuration > 0 into @duration__DELIMITER__
- RETURN @duration__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestplandays`;
-CREATE FUNCTION `qc_pgmtestplandays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeplanneddays($project,'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealdays`;
-CREATE FUNCTION `qc_pgmtestrealdays`($project int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmspecifiedtypeactualdays($project,'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddesigntplandays`;
-CREATE FUNCTION `qc_prddesigntplandays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddesigntrealdays`;
-CREATE FUNCTION `qc_prddesigntrealdays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'design') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddevelplandays`;
-CREATE FUNCTION `qc_prddevelplandays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prddevelrealdays`;
-CREATE FUNCTION `qc_prddevelrealdays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'dev') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdrequestplandays`;
-CREATE FUNCTION `qc_prdrequestplandays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdrequestrealdays`;
-CREATE FUNCTION `qc_prdrequestrealdays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'request') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdtestplandays`;
-CREATE FUNCTION `qc_prdtestplandays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageplannedduration($project, $product, 'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_prdtestrealdays`;
-CREATE FUNCTION `qc_prdtestrealdays`($project int, $product int) RETURNS int(11) READS SQL DATA
-BEGIN
- select qc_pgmstageactualduration($project, $product, 'qa') as days into @days__DELIMITER__
- return @days__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesgignrealesthours`;
-CREATE FUNCTION `qc_pgmdesgignrealesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmesthoursbytype($project, 'design')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdesignrealhours`;
-CREATE FUNCTION `qc_pgmdesignrealhours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmrealhoursbytype($project, 'design')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealesthours`;
-CREATE FUNCTION `qc_pgmdevelrealesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmesthoursbytype($project, 'devel')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmdevelrealhours`;
-CREATE FUNCTION `qc_pgmdevelrealhours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmrealhoursbytype($project, 'devel')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealesthours`;
-CREATE FUNCTION `qc_pgmrealesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_task where project=$project and parent >= 0 and status != 'cancel' and deleted = '0' into @estimate__DELIMITER__
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmesthoursbytype`;
-CREATE FUNCTION `qc_pgmesthoursbytype`($project int, $type char(30)) RETURNS float(10,2) READS SQL DATA
-BEGIN
- select CAST(sum(estimate) as DECIMAL(10,2)) as estimate from zt_task where project=$project and type = $type and parent >= 0 and status != 'cancel' and deleted = '0' into @estimate__DELIMITER__
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealhours`;
-CREATE FUNCTION `qc_pgmrealhours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- select CAST(sum(consumed) as DECIMAL(10,2)) as consumed from zt_task where project=$project and parent >= 0 and status != 'cancel' and deleted = '0' into @consumed__DELIMITER__
- return @consumed__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrealhoursbytype`;
-CREATE FUNCTION `qc_pgmrealhoursbytype`($project int, $type char(30)) RETURNS float(10,2) READS SQL DATA
-BEGIN
- select CAST(sum(consumed) as DECIMAL(10,2)) as consumed from zt_task where project=$project and type = $type and parent >= 0 and status != 'cancel' and deleted = '0' into @consumed__DELIMITER__
- return @consumed__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealesthours`;
-CREATE FUNCTION `qc_pgmrequestrealesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmesthoursbytype($project, 'request')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmrequestrealhours`;
-CREATE FUNCTION `qc_pgmrequestrealhours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmrealhoursbytype($project, 'request')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealesthours`;
-CREATE FUNCTION `qc_pgmtestrealesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmesthoursbytype($project, 'test')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmtestrealhours`;
-CREATE FUNCTION `qc_pgmtestrealhours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
-return qc_pgmrealhoursbytype($project, 'test')__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdevelfirstesthours`;
-CREATE FUNCTION `qc_getdevelfirstesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(devEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdesignfirstesthours`;
-CREATE FUNCTION `qc_getdesignfirstesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(designEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getstoryfirstesthours`;
-CREATE FUNCTION `qc_getstoryfirstesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_gettestfirstesthours`;
-CREATE FUNCTION `qc_gettestfirstesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(testEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getfirstesthours`;
-CREATE FUNCTION `qc_getfirstesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(taskEst) as estimate FROM zt_object WHERE id in(SELECT MIN(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdevlastesthours`;
-CREATE FUNCTION `qc_getdevlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(devEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getrequestlastesthours`;
-CREATE FUNCTION `qc_getrequestlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(requestEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_gettestlastesthours`;
-CREATE FUNCTION `qc_gettestlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(testEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getdesignlastesthours`;
-CREATE FUNCTION `qc_getdesignlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(designEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_getlastesthours`;
-CREATE FUNCTION `qc_getlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- SELECT sum(taskEst) as estimate FROM zt_object WHERE id in(SELECT MAX(id) FROM zt_object WHERE project = $project and category = 'PP' and type = 'taged' and product in (select product from zt_projectproduct where project = $project) group by `product`) into @estimate__DELIMITER__
-
- return @estimate__DELIMITER__
-END;
-
-DROP FUNCTION IF EXISTS `qc_pgmlastesthours`;
-CREATE FUNCTION `qc_pgmlastesthours`($project int) RETURNS float(10,2) READS SQL DATA
-BEGIN
- declare estimate float(10,2) default 0__DELIMITER__
- declare inited int default 0__DELIMITER__
- select qc_cminited($project,'PP') into inited__DELIMITER__
- IF inited = 1 THEN
- select qc_getlastesthours($project) into estimate__DELIMITER__
- return estimate__DELIMITER__
- ELSE
- return 0__DELIMITER__
- END IF__DELIMITER__
-END;
-
-- DROP TABLE IF EXISTS `zt_demandpool`;
CREATE TABLE `zt_demandpool` (
`id` int(8) NOT NULL AUTO_INCREMENT,
diff --git a/doc/CHANGELOG b/doc/CHANGELOG
index c38222300d..cfbf5efaa6 100644
--- a/doc/CHANGELOG
+++ b/doc/CHANGELOG
@@ -1,3 +1,7 @@
+2024-09-30 20.7.1
+完成的需求
+修复的Bug
+
2024-09-14 20.7
完成的需求
开源版:
diff --git a/extension/xuanxuan/extension/xuan/misc/ext/control/ajaxgetpackagesize.php b/extension/xuanxuan/extension/xuan/misc/ext/control/ajaxgetpackagesize.php
index 3e2fa1883e..6dc4b7d5c7 100644
--- a/extension/xuanxuan/extension/xuan/misc/ext/control/ajaxgetpackagesize.php
+++ b/extension/xuanxuan/extension/xuan/misc/ext/control/ajaxgetpackagesize.php
@@ -3,14 +3,16 @@ class myMisc extends misc
{
/**
* Ajax get client package size.
- *
+ *
+ * @param string $type
+ * @param string $fileName
* @access public
* @return void
*/
- public function ajaxGetPackageSize()
+ public function ajaxGetPackageSize($type = 'client', $fileName = 'zentaoclient.zip')
{
$account = $this->app->user->account;
- $packageFile = $this->app->wwwRoot . 'data/client/' . $account . '/zentaoclient.zip';
+ $packageFile = $this->app->wwwRoot . "data/{$type}/{$account}/{$fileName}";
$size = 0;
if(file_exists($packageFile))
diff --git a/lib/dbh/dbh.class.php b/lib/dbh/dbh.class.php
index df1a39e2f3..6574c38500 100644
--- a/lib/dbh/dbh.class.php
+++ b/lib/dbh/dbh.class.php
@@ -854,4 +854,55 @@ class dbh
$lastAction = $this->pdo->query($sql)->fetch();
return $lastAction ? (int)$lastAction->id : false;
}
+
+ /**
+ * 安装时检查数据库用户权限。
+ * Check user privilege.
+ *
+ * @access public
+ * @return string
+ */
+ public function checkUserPriv(): string
+ {
+ if($this->config->driver == 'mysql')
+ {
+ $user = $this->config->user;
+ $host = ($this->config->host == 'localhost' || $this->config->host == '127.0.0.1') ? 'localhost' : '%';
+
+ // 获取当前用户的所有权限
+ $privPairs = array();
+ $privList = $this->pdo->query("SELECT PRIVILEGE_TYPE FROM information_schema.USER_PRIVILEGES WHERE GRANTEE LIKE '%$user%';")->fetchAll();
+ foreach($privList as $priv)
+ {
+ $privPairs[$priv->PRIVILEGE_TYPE] = 1;
+ }
+
+ // 禅道所需的权限
+ $requiredPrivs = array('SELECT', 'INSERT', 'UPDATE', 'DELETE', 'DROP', 'CREATE', 'ALTER', 'INDEX', 'CREATE VIEW');
+
+ $missingPrivs = array();
+ foreach($requiredPrivs as $priv)
+ {
+ if(!isset($privPairs[$priv])) $missingPrivs[] = $priv;
+ }
+
+ $sql = '';
+ if(!empty($missingPrivs))
+ {
+ $sql .= 'GRANT ';
+ foreach($missingPrivs as $priv)
+ {
+ $sql .= $priv . ',';
+ }
+
+ $sql = rtrim($sql, ',');
+ $sql .= " ON *.* TO '$user'@'$host';" . '\n';
+ $sql .= 'FLUSH PRIVILEGES;';
+ }
+
+ return $sql;
+ }
+
+ return '';
+ }
}
diff --git a/lib/duckdb/duckdb.class.php b/lib/duckdb/duckdb.class.php
index 81207c3b23..de3cd319fb 100644
--- a/lib/duckdb/duckdb.class.php
+++ b/lib/duckdb/duckdb.class.php
@@ -195,6 +195,7 @@ class duckdb
$sql = preg_replace($ztpattern, $replace, $sql);
$sql = preg_replace($ztvpattern, $replace, $sql);
+ $sql = str_replace('zt_action.parquet', 'zt_action_*.parquet', $sql);
$sql = str_replace('__biPath__', $this->tmpPath, $sql);
return $sql;
}
diff --git a/lib/zdb/zdb.class.php b/lib/zdb/zdb.class.php
index 9650e83357..d9598b2717 100644
--- a/lib/zdb/zdb.class.php
+++ b/lib/zdb/zdb.class.php
@@ -51,7 +51,7 @@ class zdb
while($table = $stmt->fetch(PDO::FETCH_ASSOC))
{
$tableType = strtolower($table['Table_type']);
- if($type == 'base' and $tableType != 'base table') continue;
+ if($type == 'base' && $tableType != 'base table' && $tableType != 'table') continue;
$tableName = $table["Tables_in_{$config->db->name}"];
$allTables[$tableName] = $tableType == 'base table' ? 'table' : $tableType;
diff --git a/lib/zin/wg/backbtn/v1.php b/lib/zin/wg/backbtn/v1.php
index 11e9ba89f7..7b0e3a2dbb 100644
--- a/lib/zin/wg/backbtn/v1.php
+++ b/lib/zin/wg/backbtn/v1.php
@@ -60,7 +60,7 @@ class backBtn extends btn
'projectstory' => 'projectstory-story',
'build' => 'execution-build,build-view,project-index,kanban-view,testtask-browse,projectbuild-browse,my-effort,my-index,project-dynamic,execution-dynamic,project-view,execution-view',
'projectbuild' => 'projectbuild-browse,projectbuild-view,project-index',
- 'repo' => 'repo-maintain,repo-log,repo-browse,repo-view,repo-review,mr-view,repo-browsewebhooks',
+ 'repo' => 'repo-maintain,repo-log,repo-browse,repo-view,repo-review,mr-view,repo-browsewebhooks,repo-browserule',
'mr' => 'pullreq-browse,mr-browse',
'pullreq' => 'pullreq-browse',
'compile' => 'compile-browse',
diff --git a/lib/zin/wg/bugrelatedlist/v1.php b/lib/zin/wg/bugrelatedlist/v1.php
index d9f2037f29..a91e1e754f 100644
--- a/lib/zin/wg/bugrelatedlist/v1.php
+++ b/lib/zin/wg/bugrelatedlist/v1.php
@@ -109,6 +109,7 @@ class bugRelatedList extends relatedList
/* Linked MR. */
$linkMRList = isset($bug->linkMRTitles) ? $bug->linkMRTitles :array();
+ $linkedPRs = $this->prop('linkedPRs', data('linkedPRs'));
if(helper::hasFeature('devops'))
{
$data['mr'] = array
@@ -128,6 +129,26 @@ class bugRelatedList extends relatedList
}
);
+ if($linkedPRs)
+ {
+ $data['pr'] = array
+ (
+ 'title' => $lang->bug->linkPR,
+ 'items' => $linkedPRs,
+ 'url' => hasPriv('pullreq', 'view') ? createLink('pullreq', 'view', 'MRID={id}') : false,
+ 'props' => array('data-app' => 'devops'),
+ 'onRender' => function($item, $mr) use($lang)
+ {
+ $item['titleClass'] = 'w-0 flex-1';
+ $statusClass = $mr->status;
+ if($mr->status == 'opened') $statusClass = 'draft';
+ if($mr->status == 'merged') $statusClass = 'done';
+ $item['content'] = array('html' => "" . zget($lang->mr->statusList, $mr->status) . '');
+ return $item;
+ }
+ );
+ }
+
$data['linkCommit'] = array
(
'title' => $lang->bug->linkCommit,
diff --git a/lib/zin/wg/casebasicinfo/v1.php b/lib/zin/wg/casebasicinfo/v1.php
index 0066eab956..b80e0e5008 100644
--- a/lib/zin/wg/casebasicinfo/v1.php
+++ b/lib/zin/wg/casebasicinfo/v1.php
@@ -166,7 +166,8 @@ class caseBasicInfo extends wg
$case = $this->prop('case', data('case'));
if(!$case) return array();
- $isLibCase = $this->prop('isLibCase', data('isLibCase'));
+ $isLibCase = $this->prop('isLibCase', data('isLibCase'));
+ $scenes = $this->prop('scenes', data('scenes'));
$items = array();
if($isLibCase)
@@ -184,6 +185,7 @@ class caseBasicInfo extends wg
if($case->product && !$product->shadow) $items[$lang->testcase->product] = hasPriv('product', 'view') ? array('control' => 'link', 'url' => createLink('product', 'view', "productID={$case->product}"), 'text' => $product->name) : $product->name;
if($case->branch && $product->type != 'normal') $items[$branchLabel] = hasPriv('testcase', 'browse') ? array('control' => 'link', 'url' => createLink('testcase', 'browse', "productID={$case->product}&branch={$case->branch}"), 'text' => $branchName) : $branchName;
$items[$lang->testcase->module] = array('children' => wg($this->getModule($case)));
+ $items[$lang->testcase->scene] = array('control' => 'text', 'text' => zget($scenes, $case->scene, ''));
$items[$lang->testcase->story] = array('children' => wg($this->getStory($case)));
}
diff --git a/lib/zin/wg/filter/v1.php b/lib/zin/wg/filter/v1.php
index bad03b8ba7..38dfa98962 100644
--- a/lib/zin/wg/filter/v1.php
+++ b/lib/zin/wg/filter/v1.php
@@ -83,7 +83,7 @@ class filter extends wg
protected function buildControl(string $type): node|array
{
- if($type == 'select') return $this->buildPicker();
+ if($type == 'select' || $type == 'multipleselect') return $this->buildPicker();
if($type == 'date') return $this->buildDatePicker();
if($type == 'datetime') return $this->buildDatetimePicker();
return $this->buildInput();
diff --git a/lib/zin/wg/formpanel/v1.php b/lib/zin/wg/formpanel/v1.php
index 3f9ed358a9..1ac6c7571d 100644
--- a/lib/zin/wg/formpanel/v1.php
+++ b/lib/zin/wg/formpanel/v1.php
@@ -65,8 +65,7 @@ class formPanel extends panel
'pinnedItems?: array|string', // 固定显示的表单项。
'customBtn?: array|bool', // 是否显示表单自定义按钮。
'customFields?: array=[]', // @deprecated 自定义表单项。
- 'showExtra?: bool=true', // 是否显示工作流字段。
- 'submitDisabledValue?: bool=false' // 是否将disabled的字段传入后端。
+ 'showExtra?: bool=true' // 是否显示工作流字段。
);
public static function getPageJS(): ?string
@@ -295,7 +294,6 @@ class formPanel extends panel
(
set::id($formID),
set::className($this->prop('formClass')),
- set::ajax(array('submitDisabledValue' => $this->prop('submitDisabledValue'))),
set($this->props->pick($formProps)),
$this->children(),
$this->prop('showExtra') && !$fields ? $this->buildExtraMain() : null,
diff --git a/lib/zin/wg/queryfiltermodal/v1.php b/lib/zin/wg/queryfiltermodal/v1.php
index a6a3e81f78..233e518ff3 100644
--- a/lib/zin/wg/queryfiltermodal/v1.php
+++ b/lib/zin/wg/queryfiltermodal/v1.php
@@ -57,6 +57,8 @@ class queryFilterModal extends wg
)
);
+ $defaultWgList = array('date' => 'datePicker', 'datetime' => 'datetimePicker', 'input' => 'input', 'select' => 'picker', 'multipleselect' => 'picker');
+
$type = $this->buildControl
(
'type',
@@ -73,7 +75,7 @@ class queryFilterModal extends wg
),
picker
(
- setClass(array('hidden' => $value['type'] !== 'select')),
+ setClass(array('hidden' => $defaultWgList[$value['type']] !== 'picker')),
set::name("typeOption"),
set::items($lang->dataview->varFilter->selectList),
set::value($value['typeOption'])
@@ -81,15 +83,13 @@ class queryFilterModal extends wg
)
);
- $defaultWgList = array('date' => 'datePicker', 'datetime' => 'datetimePicker', 'input' => 'input', 'select' => 'picker');
-
list($defaultType, $defaultItems, $defaultValue) = array($value['type'], $value['items'], $value['default']);
$default = $this->buildControl
(
'default',
'basis-48',
- createWg($defaultWgList[$defaultType], set(array('name' => 'default', 'items' => $defaultItems, 'value' => $defaultValue)))
+ createWg($defaultWgList[$defaultType], set(array('name' => 'default', 'items' => $defaultItems, 'value' => $defaultValue, 'multiple' => ($defaultType == 'multipleselect' ? true : false))))
);
return formRow
diff --git a/lib/zin/wg/sqlbuilder/js/v1.js b/lib/zin/wg/sqlbuilder/js/v1.js
index dc564695dd..512250e784 100644
--- a/lib/zin/wg/sqlbuilder/js/v1.js
+++ b/lib/zin/wg/sqlbuilder/js/v1.js
@@ -37,7 +37,7 @@ window.changeBuilderTable = function(event)
if(name == 'from')
{
- from.table = value;
+ from.table = value;
from.select = [];
}
if(name.startsWith('left'))
diff --git a/lib/zin/wg/sqlbuilder/v1.php b/lib/zin/wg/sqlbuilder/v1.php
index 3e260f6e67..d252cff26b 100644
--- a/lib/zin/wg/sqlbuilder/v1.php
+++ b/lib/zin/wg/sqlbuilder/v1.php
@@ -177,7 +177,7 @@ class sqlBuilder extends wg
btn
(
setID('addJoinTable'),
- setClass('p-0 ml-4'),
+ setClass('ml-2 text-primary'),
set('data-index', -1),
set::type('ghost'),
set::icon('plus'),
diff --git a/lib/zin/wg/storyrelatedlist/v1.php b/lib/zin/wg/storyrelatedlist/v1.php
index b6e86683a9..a1838dd82f 100644
--- a/lib/zin/wg/storyrelatedlist/v1.php
+++ b/lib/zin/wg/storyrelatedlist/v1.php
@@ -14,6 +14,7 @@ class storyRelatedList extends relatedList
'releases' => '?array', // 关联的发布列表。
'storyProducts' => '?array', // 需求产品信息。
'linkedMRs' => '?array', // 需求 MR 信息。
+ 'linkedPRs' => '?array', // 需求 PR 信息。
'linkedCommits' => '?linkedCommits', // 需求提交信息。
'story' => '?object' // 当前需求。
);
@@ -36,6 +37,7 @@ class storyRelatedList extends relatedList
$builds = $this->prop('builds', data('builds'));
$releases = $this->prop('releases', data('releases'));
$linkedMRs = $this->prop('linkedMRs', data('linkedMRs'));
+ $linkedPRs = $this->prop('linkedPRs', data('linkedPRs'));
$linkedCommits = $this->prop('linkedCommits', data('linkedCommits'));
$data = array();
@@ -108,6 +110,26 @@ class storyRelatedList extends relatedList
}
);
+ if($linkedPRs)
+ {
+ $data['pr'] = array
+ (
+ 'title' => $lang->story->linkPR,
+ 'items' => $linkedPRs,
+ 'url' => hasPriv('pullreq', 'view') ? createLink('pullreq', 'view', 'MRID={id}') : false,
+ 'props' => array('data-app' => 'devops'),
+ 'onRender' => function($item, $mr) use($lang)
+ {
+ $item['titleClass'] = 'w-0 flex-1';
+ $statusClass = $mr->status;
+ if($mr->status == 'opened') $statusClass = 'draft';
+ if($mr->status == 'merged') $statusClass = 'done';
+ $item['content'] = array('html' => "" . zget($lang->mr->statusList, $mr->status) . '');
+ return $item;
+ }
+ );
+ }
+
$data['commit'] = array
(
'title' => $lang->story->linkCommit,
diff --git a/lib/zin/wg/taskmiscinfo/v1.php b/lib/zin/wg/taskmiscinfo/v1.php
index e32d2fbd18..595ca3cd74 100644
--- a/lib/zin/wg/taskmiscinfo/v1.php
+++ b/lib/zin/wg/taskmiscinfo/v1.php
@@ -25,6 +25,7 @@ class taskMiscInfo extends relatedList
{
$canViewMR = common::hasPriv('mr', 'view');
$linkMRList = $this->prop('linkMRTitles', data('linkMRTitles'));
+ $linkedPRs = $this->prop('linkedPRs', data('linkedPRs'));
$data['mr'] = array
(
'title' => $lang->task->linkMR,
@@ -42,6 +43,26 @@ class taskMiscInfo extends relatedList
}
);
+ if($linkedPRs)
+ {
+ $data['pr'] = array
+ (
+ 'title' => $lang->task->linkPR,
+ 'items' => $linkedPRs,
+ 'url' => hasPriv('pullreq', 'view') ? createLink('pullreq', 'view', 'MRID={id}') : false,
+ 'props' => array('data-app' => 'devops'),
+ 'onRender' => function($item, $mr) use($lang)
+ {
+ $item['titleClass'] = 'w-0 flex-1';
+ $statusClass = $mr->status;
+ if($mr->status == 'opened') $statusClass = 'draft';
+ if($mr->status == 'merged') $statusClass = 'done';
+ $item['content'] = array('html' => "" . zget($lang->mr->statusList, $mr->status) . '');
+ return $item;
+ }
+ );
+ }
+
$linkedCommits = $this->prop('linkCommits', data('linkCommits'));
$data['linkCommit'] = array
(
diff --git a/lib/zin/wg/think3c/js/v1.js b/lib/zin/wg/think3c/js/v1.js
index 491c6ccda7..b78b66b27a 100644
--- a/lib/zin/wg/think3c/js/v1.js
+++ b/lib/zin/wg/think3c/js/v1.js
@@ -9,7 +9,7 @@ const colors = ['#CFE7FE', '#DCEFF9', '#E0EBFC', '#DBE9FA', '#D4EEE9', '#E4DFF7'
*/
function getModelColors()
{
- const model = $('.model-canvas').data('model');
+ const model = $(`#canvas_${model3cKey}`).closest('.model-canvas').data('model');
let modelColors = colors;
const colorGroup = {};
if(colorGroup[`color${model}`] && Array.isArray(colorGroup[`color${model}`])) modelColors = colorGroup[`color${model}`];
@@ -26,10 +26,10 @@ function getModelColors()
*/
window.initThinkCanvas = function()
{
- const canvas = $('#canvas')[0];
+ const canvas = $(`#canvas_${model3cKey}`)[0];
const ctx = canvas.getContext('2d');
const image = new Image();
- const model = $('.model-canvas').data('model');
+ const {model, mode} = $(`#canvas_${model3cKey}`).closest('.model-canvas').data();
image.src = `data/thinmory/thumbnail/init${model}.png`;
image.onload = function()
@@ -49,28 +49,36 @@ window.initThinkCanvas = function()
const pixelData = data.pixelData;
displayColoredImage(data.image);
- renderRegionInput(coloredRegions);
- /* 点击画布外区域取消高亮。*/
- /* Click on the area outside the canvas to unhighlight.*/
- $(document).on('click', function(event)
+ if(mode == 'preview')
{
- const rect = canvas.getBoundingClientRect();
- const canvasX = rect.left;
- const canvasY = rect.top;
- const mouseX = event.clientX;
- const mouseY = event.clientY;
+ renderRegionInput(coloredRegions);
- /* 恢复整个画布的原始状态。 */
- ctx.putImageData(pixelData, 0, 0);
-
- /* 检测鼠标位置是否在特定区域内。 */
- /* Check if the mouse position is within a specific area. */
- if(mouseX >= canvasX && mouseX <= (canvasX + canvas.width) && mouseY >= canvasY && mouseY <= (canvasY + canvas.height))
+ /* 点击画布外区域取消高亮。*/
+ /* Click on the area outside the canvas to unhighlight.*/
+ $(document).on('click', function(event)
{
- handleCanvasClick(mouseX, mouseY, canvas, ctx, coloredRegions);
- }
- });
+ const rect = canvas.getBoundingClientRect();
+ const canvasX = rect.left;
+ const canvasY = rect.top;
+ const mouseX = event.clientX;
+ const mouseY = event.clientY;
+
+ /* 恢复整个画布的原始状态。 */
+ ctx.putImageData(pixelData, 0, 0);
+
+ /* 检测鼠标位置是否在特定区域内。 */
+ /* Check if the mouse position is within a specific area. */
+ if(mouseX >= canvasX && mouseX <= (canvasX + canvas.width) && mouseY >= canvasY && mouseY <= (canvasY + canvas.height))
+ {
+ handleCanvasClick(mouseX, mouseY, canvas, ctx, coloredRegions);
+ }
+ });
+ }
+ else
+ {
+ renderRegionTitles(coloredRegions);
+ }
});
};
@@ -79,6 +87,65 @@ window.initThinkCanvas = function()
if(image.complete && image.naturalWidth != 0) image.onload();
}
+/**
+ * 计算卡片位置。
+ * Calculate card position.
+ *
+ * @param object region
+ * @access public
+ * @return void
+ */
+function calculateCardPosition(region)
+{
+ const h = 300; // 卡片高度
+ const minW = 256; // 最小宽度
+ const maxW = 400; // 最大宽度
+ const d = 10; // 间距
+ const rows = flattenData(region.rows);
+ const rowsCount = rows.length;
+
+ let r = 0;
+ while (r < rowsCount)
+ {
+ let totalWidth = 0;
+ let validStartRow = -1;
+
+ for(let i = r; i < r + h && i < rowsCount; i++)
+ {
+ if(rows[i]?.right) totalWidth += rows[i].right - rows[i].left;
+ if(totalWidth >= minW)
+ {
+ validStartRow = r;
+ break;
+ }
+ }
+
+ if(validStartRow !== -1)
+ {
+ let left = rows[validStartRow]?.left || 0;
+ let right = rows[Math.min(validStartRow + h - 1, rowsCount - 1)]?.right || 0;
+ let rowN = Math.floor((right - left + d) / (minW + d));
+ let w = (right - left + d) / rowN;
+
+ for(let i = 0; i < rowN; i++)
+ {
+ let blockLeft = left + i * (w + d);
+ let blockTop = rows[validStartRow].top;
+ let blockWidth = Math.min(w, maxW);
+ let blockHeight = h;
+
+ // TODO: 绘制卡片
+ console.log(`Block ${i + 1}: Left: ${blockLeft}, Top: ${blockTop}, Width: ${blockWidth}, Height: ${blockHeight}`);
+ }
+ r += h;
+ }
+ else
+ {
+ r++;
+ }
+ }
+}
+
/**
* 处理画布点击。
* handle canvas click.
@@ -105,7 +172,7 @@ function handleCanvasClick(mouseX, mouseY, canvas, ctx, coloredRegions)
if(isInRegion)
{
- if($(`#input_${index}`).length) $(`#input_${index}`)[0].focus();
+ if($(`#input_${model3cKey}_${index}`).length) $(`#input_${model3cKey}_${index}`)[0].focus();
renderHighlightedRegion(index, coloredRegions[index], ctx);
}
});
@@ -172,6 +239,11 @@ function binarizeImage(imageData)
*/
function getCanvasSize(width = 0, height = 0)
{
+ if(model3cKey == 'link') return {width: 420, height: 400};
+
+ const mode = $(`#canvas_${model3cKey}`).closest('.model-canvas').data('mode');
+ if(mode == 'view') return {width: 2000, height: 2000};
+
const maxWidth = $('.think-model-content').length ? ($('.think-model-content').width() - 50) : 400;
const maxHeight = maxWidth;
@@ -265,7 +337,8 @@ function findRegions(pixels, width, height)
{
const visited = {};
const regions = [];
-
+ const mode = $(`#canvas_${model3cKey}`).closest('.model-canvas').data('mode');
+ const minArea = mode == 'view' ? 500 : 100;
for(let y = 0; y < height; y++)
{
for(let x = 0; x < width; x++)
@@ -277,7 +350,7 @@ function findRegions(pixels, width, height)
/* 过滤掉小区域。 */
/* Filter out small regions. */
- if(region.area > 100)
+ if(region.area > minArea)
{
region.rows.forEach((row, key) => {
region.rows[key] = processRegionRows(row);
@@ -383,6 +456,7 @@ window.drawRegionInput = function(canvas, region, colorIndex, clientLang, blocks
const centerY = (region.minY + region.maxY) / 2;
const boxWidth = 60;
const boxHeight = 32;
+ const disabled = $(`#canvas_${model3cKey}`).closest('.model-canvas').data('disabled');
let left = centerX - boxWidth / 2;
let top = centerY - boxHeight / 2;
@@ -424,9 +498,10 @@ window.drawRegionInput = function(canvas, region, colorIndex, clientLang, blocks
input.type = 'text';
input.value = value;
input.title = value;
- input.id = `input_${colorIndex}`;
+ input.id = `input_${model3cKey}_${colorIndex}`;
input.name = `blocks[]`;
input.placeholder = blockName;
+ input.disabled = disabled;
input.setAttribute('data-index', colorIndex);
input.setAttribute('data-block', value);
Object.assign(input.style, styles);
@@ -434,6 +509,83 @@ window.drawRegionInput = function(canvas, region, colorIndex, clientLang, blocks
canvas.parentNode.appendChild(input);
}
+/**
+ * 绘制区域标题。
+ * Draw a region title.
+ *
+ * @param object canvas
+ * @param object region
+ * @param number colorIndex
+ * @param array blocks
+ * @access public
+ * @return void
+ */
+window.drawRegionTitle = function(canvas, region, colorIndex, blocks)
+{
+ const centerX = (region.minX + region.maxX) / 2;
+ const centerY = (region.minY + region.maxY) / 2;
+ const boxWidth = 120;
+ const boxHeight = 48;
+
+ let left = centerX - boxWidth / 2;
+ let top = centerY - boxHeight / 2;
+ let bottom = 0;
+
+ const positionMap = {
+ 0: {left: left, top: 40},
+ 1: {left: left - 40, top: top + 180},
+ 2: {left: left + 100, top: top + 180},
+ 3: {left: left, top: top - 240},
+ 4: {left: left + 260, top: top - 450},
+ 5: {left: left - 240, top: top - 450},
+ 6: {left: left, top: 0, bottom: 160}
+ };
+
+ if(colorIndex in positionMap)
+ {
+ const {left: newLeft, top: newTop, bottom: newBottom = 'unset'} = positionMap[colorIndex];
+ left = newLeft;
+ top = newTop;
+ bottom = newBottom;
+ }
+
+ const styles = {
+ left: left ? `${left}px` : 'unset',
+ top: top ? `${top}px` : 'unset',
+ bottom: bottom ? `${bottom}px` : 'unset'
+ };
+
+ const block = String.fromCharCode(97 + colorIndex);
+ const $title = document.createElement('div');
+ const value = typeof blocks[colorIndex] == 'string' ? blocks[colorIndex] : block;
+ $title.innerHTML = value;
+ $title.id = `title_${colorIndex}`;
+ $title.className = 'w-28 h-12 p-1 item-step-title text-clip text-center absolute';
+ Object.assign($title.style, styles);
+
+ canvas.parentNode.appendChild($title);
+}
+
+/**
+ * 渲染区域标题。
+ * Render region titles.
+ *
+ * @param array regions
+ * @access public
+ * @return void
+ */
+function renderRegionTitles(regions)
+{
+ const {model, blocks} = $(`#canvas_${model3cKey}`).closest('.model-canvas').data();
+ let drawTitleFunc = `drawRegionTitleOf${model}`;
+ drawTitleFunc = (drawTitleFunc in window) ? window[drawTitleFunc] : window['drawRegionTitle'];
+ const canvas = $(`#canvas_${model3cKey}`)[0];
+
+ regions.forEach((region, index) => {
+ if(!$(`#title_${index}`).length) drawTitleFunc(canvas, region, index, blocks);
+ });
+}
+
/**
* 渲染区域输入框。
* Render region inputs.
@@ -444,15 +596,13 @@ window.drawRegionInput = function(canvas, region, colorIndex, clientLang, blocks
*/
function renderRegionInput(regions)
{
- const model = $('.model-canvas').data('model');
- const clientLang = $('.model-canvas').data('clientLang');
- const blocks = $('.model-canvas').data('blocks');
+ const {model, blocks, clientLang} = $(`#canvas_${model3cKey}`).closest('.model-canvas').data();
let drawInputFunc = `drawRegionInputOf${model}`;
drawInputFunc = (drawInputFunc in window) ? window[drawInputFunc] : window['drawRegionInput'];
- const canvas = $('#canvas')[0];
+ const canvas = $(`#canvas_${model3cKey}`)[0];
regions.forEach((region, index) => {
- if(!$(`#input_${index}`).length) drawInputFunc(canvas, region, index, clientLang, blocks);
+ if(!$(`#input_${model3cKey}_${index}`).length) drawInputFunc(canvas, region, index, clientLang, blocks);
});
}
@@ -514,7 +664,7 @@ function colorRegions(binaryImageData)
*/
function displayColoredImage(coloredImageData)
{
- const canvas = $('#canvas')[0];
+ const canvas = $(`#canvas_${model3cKey}`)[0];
const ctx = canvas.getContext('2d');
const img = new Image();
diff --git a/lib/zin/wg/think3c/v1.php b/lib/zin/wg/think3c/v1.php
index b70e256350..bdcf516c71 100644
--- a/lib/zin/wg/think3c/v1.php
+++ b/lib/zin/wg/think3c/v1.php
@@ -6,6 +6,11 @@ requireWg('thinkModel');
class think3c extends thinkModel
{
+ protected static array $defineProps = array
+ (
+ 'key?: string="view"',
+ 'disabled?=false: bool',
+ );
public static function getPageCSS(): ?string
{
return file_get_contents(__DIR__ . DS . 'css' . DS . 'v1.css');
@@ -20,17 +25,15 @@ class think3c extends thinkModel
{
global $lang, $app;
+ list($blocks, $mode, $disabled, $key) = $this->prop(array('blocks', 'mode', 'disabled', 'key'));
jsVar('blockName', $lang->thinkwizard->placeholder->blockName);
- list($blocks, $mode) = $this->prop(array('blocks', 'mode'));
+ jsVar('model3cKey', $key);
return div
(
- setData('clientLang', $app->getClientLang()),
- setData('model', '3c'),
- setData('mode', $mode),
- setData('blocks', $blocks),
- setClass('model-canvas relative flex justify-center'),
- h::canvas(setID('canvas')),
+ setData(array('clientLang' => $app->getClientLang(), 'model' => '3c', 'mode' => $mode, 'blocks' => $blocks, 'disabled' => $disabled)),
+ setClass('model-canvas relative flex justify-center', "model-canvas-$key"),
+ h::canvas(setID('canvas_' . $key)),
on::blur('.model-canvas input')->do('
const index = $(this).data("index");
const block = $(this).data("block");
diff --git a/lib/zin/wg/thinkstep/v1.php b/lib/zin/wg/thinkstep/v1.php
index 208ef195fa..f787e01e78 100644
--- a/lib/zin/wg/thinkstep/v1.php
+++ b/lib/zin/wg/thinkstep/v1.php
@@ -44,7 +44,9 @@ class thinkStep extends wg
$title = $action == 'detail' ? sprintf($lang->thinkstep->info, $lang->thinkstep->$basicType) : sprintf($lang->thinkstep->formTitle[$type], $lang->thinkstep->$typeLang);
$canEdit = common::hasPriv('thinkstep', 'edit');
$canDelete = common::hasPriv('thinkstep', 'delete');
- $canLink = $wizard->model === '3c' && ($type === 'checkbox' || $type === 'radio' || $type === 'multicolumn');
+ $linkType = $type === 'checkbox' || $type === 'radio' || $type === 'multicolumn';
+ $linkmodel = !$isRun && $wizard->model === '3c';
+ $canLink = common::hasPriv('thinkstep', 'link') && $linkmodel && $linkType;
return div
(
@@ -65,7 +67,8 @@ class thinkStep extends wg
(
setClass('btn ghost text-gray w-5 h-5 mr-1'),
set::icon('link'),
- set::url(createLink('thinkstep', 'link')),
+ set::url(createLink('thinkstep', 'link', "marketID={$marketID}&stepID={$item->id}")),
+ set::hint($lang->thinkstep->actions['link']),
set('data-toggle', 'modal'),
set('data-dismiss', 'modal'),
set('data-size', 'sm'),
@@ -78,12 +81,14 @@ class thinkStep extends wg
(
setClass('btn ghost text-gray w-5 h-5'),
set::icon('edit'),
+ set::hint($lang->thinkstep->actions['edit']),
set::url(createLink('thinkstep', 'edit', "marketID={$marketID}&stepID={$item->id}")),
) : null,
$canDelete ? ((!$item->existNotNode && empty($quotedQuestions)) ? btn
(
setClass('btn ghost text-gray w-5 h-5 ml-1 ajax-submit'),
set::icon('trash'),
+ set::hint($lang->thinkstep->actions['delete']),
setData('url', createLink('thinkstep', 'delete', "marketID={$marketID}&stepID={$item->id}")),
setData('confirm', $lang->thinkstep->deleteTips[$basicType])
) : icon
diff --git a/lib/zin/wg/thinkstepmenu/js/v1.js b/lib/zin/wg/thinkstepmenu/js/v1.js
index 1baa287c09..3b5da7feac 100644
--- a/lib/zin/wg/thinkstepmenu/js/v1.js
+++ b/lib/zin/wg/thinkstepmenu/js/v1.js
@@ -1,6 +1,10 @@
/* 进入页面,树结构为展开状态。*/
/* Entering the page, the step tree is in an expanded state.*/
-setTimeout(function(){if(from && !localStorage.getItem('thinkTreeFrom')) localStorage.setItem('thinkTreeFrom', from);}, 15);
+setTimeout(function()
+{
+ const from = $('.think-node-menu').data('from');
+ if(from && !localStorage.getItem('thinkTreeFrom')) localStorage.setItem('thinkTreeFrom', from);
+}, 15);
setTimeout(function()
{
const thinkTreeFrom = localStorage.getItem('thinkTreeFrom');
@@ -100,6 +104,7 @@ window.addQuestion = function(stepID, parentID, type, questionType = '')
const style = `style="margin-bottom: 6px; margin-left: calc(${parent == parentID ? 12 : 3} * (-4px)); padding-left: 12px;"`;
const className = parent == parentID ? '' : 'mt-2';
const $title = `
${untitledLangs[type]}
`;
+ const marketID = $('.think-node-menu').data('marketID');
/* 当父节点为收起状态时,展开子节点。 */
/* When the parent node is in a collapsed state, expand the child nodes. */
@@ -131,6 +136,7 @@ window.saveStep = function()
if(!name) return $(this).closest('.tree-item').remove();
const {id, addType, parent, order, wizard} = $(this).data();
const currentParent = addType == 'same' ? parent : 0;
+ const marketID = $('.think-node-menu').data('marketID');
$.ajaxSubmit({
url: $.createLink('thinkstep', 'ajaxCreate', `marketID=${marketID}¤tParent=${currentParent}¤tOrder=${order}`),
diff --git a/lib/zin/wg/thinkstepmenu/v1.php b/lib/zin/wg/thinkstepmenu/v1.php
index 566726d198..78d359153a 100644
--- a/lib/zin/wg/thinkstepmenu/v1.php
+++ b/lib/zin/wg/thinkstepmenu/v1.php
@@ -11,6 +11,8 @@ class thinkStepMenu extends wg
protected static array $defineProps = array(
'modules: array',
'wizard: object',
+ 'marketID?: int',
+ 'from?: string',
'activeKey?: int',
'hover?: bool=true',
'showAction?: bool=true',
@@ -51,7 +53,6 @@ class thinkStepMenu extends wg
private function buildMenuTree(array $items, int $parentID = 0): array
{
- jsVar('from', data('from') ?? '');
if(empty($items)) $items = $this->modules;
if(empty($items)) return array();
@@ -158,6 +159,7 @@ class thinkStepMenu extends wg
$canCreate = common::hasPriv('thinkstep', 'create');
$canEdit = common::hasPriv('thinkstep', 'edit');
$canDelete = common::hasPriv('thinkstep', 'delete');
+ $canLink = common::hasPriv('thinkstep', 'link');
$parentID = $item->type != 'node' ? $item->parent : $item->id;
$confirmTips = $this->lang->thinkstep->deleteTips[$item->type];
$menus = array();
@@ -186,7 +188,7 @@ class thinkStepMenu extends wg
);
}
- $marketID = data('marketID');
+ $marketID = $this->prop('marketID');
$itemHasQuoted = empty($item->hasQuoted) || $item->hasQuoted == 0;
$deleteItem = (!$item->existNotNode && $itemHasQuoted) ? array(
'key' => 'deleteNode',
@@ -203,8 +205,8 @@ class thinkStepMenu extends wg
'hint' => $item->existNotNode ? $this->lang->thinkstep->cannotDeleteNode : $this->lang->thinkstep->cannotDeleteQuestion,
);
$options = $item->type === 'question' ? json_decode($item->options) : null;
- $canLink = !empty($options) && ($options->questionType == 'checkbox' || $options->questionType === 'radio' || $options->questionType === 'multicolumn');
- $linkItem = $canLink && $options->required ? array(
+ $linkType = !empty($options) && ($options->questionType == 'checkbox' || $options->questionType === 'radio' || $options->questionType === 'multicolumn');
+ $linkItem = ($canLink && $linkType && $options->required) ? array(
'key' => 'linkNode',
'icon' => 'link',
'text' => $this->lang->thinkstep->actions['link'],
@@ -228,7 +230,7 @@ class thinkStepMenu extends wg
'url' => createLink('thinkstep', 'edit', "marketID={$marketID}&stepID={$item->id}")
) : null,
$canDelete ? $deleteItem : null,
- $wizard-> model === '3c' && $canLink ? $linkItem : null
+ $wizard->model === '3c' && $item->type == 'question' && $canLink ? $linkItem : null
), $transitionAction);
if($canCreate && (($showQuestionOfNode && $item->type == 'node') || $item->hasSameQuestion || $item->type == 'question')) $menus = array_merge($menus, array(
@@ -269,12 +271,14 @@ class thinkStepMenu extends wg
$treeProps = $this->props->pick(array('items', 'activeClass', 'activeIcon', 'activeKey', 'onClickItem', 'defaultNestedShow', 'changeActiveKey', 'isDropdownMenu', 'checkbox', 'checkOnClick', 'onCheck', 'sortable', 'onSort'));
$isInSidebar = $this->parent instanceof sidebar;
$treeType = (!empty($treeProps['onSort']) || !empty($treeProps['sortable'])) ? 'sortableTree' : 'tree';
+ list($marketID, $from) = $this->prop(array('marketID', 'from'));
return array
(
div
(
setClass('think-node-menu rounded bg-white col bg-canvas pb-3 h-full no-morph'),
+ setData(array('marketID' => $marketID, 'from' => $from ?? '')),
zui::$treeType
(
set::_id('thinkNodeMenu'),
diff --git a/lib/zin/wg/thinktableinput/js/v1.js b/lib/zin/wg/thinktableinput/js/v1.js
index 0c7c6de23b..967f14435d 100644
--- a/lib/zin/wg/thinktableinput/js/v1.js
+++ b/lib/zin/wg/thinktableinput/js/v1.js
@@ -38,24 +38,23 @@ function setLineIndex(canAddRows, fieldsCount)
* 添加行。
* Add rows.
*
- * @param event $e
+ * @access public
* @returns void
*/
-window.addRow = function(e)
+$(document).off('click', '.think-step .btn-add').on('click', '.think-step .btn-add', function()
{
- const canAddRows = $(e.target).data('canAddRows');
- const fieldsCount = $(e.target).data('fieldsCount');
+ const canAddRows = $(this).data('canAddRows');
+ const fieldsCount = $(this).data('fieldsCount');
if($('.rows-group').length >= canAddRows) return;
- const parentFormGroup = $(e.target || e).closest('.form-group');
+ const parentFormGroup = $(this).closest('.form-group');
const $newRow = $('.rows-template').clone();
- $newRow.find('.btn-add').attr('onclick', 'addRow(this)');
$newRow.removeClass('rows-template').removeClass('hidden').addClass('rows-group');
$newRow.find('textarea').val('');
parentFormGroup.after($newRow);
$newRow.find('#customFields').trigger("focus");
setLineIndex(canAddRows, fieldsCount);
-}
+})
/**
* 删除行。
@@ -64,7 +63,7 @@ window.addRow = function(e)
* @access public
* @return void
*/
-$(document).on('click', '.think-step .btn-delete', function()
+$(document).off('click', '.think-step .btn-delete').on('click', '.think-step .btn-delete', function()
{
const canAddRows = $(this).data('canAddRows');
const fieldsCount = $(this).data('fieldsCount');
diff --git a/lib/zin/wg/thinktableinput/v1.php b/lib/zin/wg/thinktableinput/v1.php
index 0c06eb8712..3d53127068 100644
--- a/lib/zin/wg/thinktableinput/v1.php
+++ b/lib/zin/wg/thinktableinput/v1.php
@@ -79,7 +79,6 @@ class thinkTableInput extends thinkQuestion
(
'plus',
setClass('mr-1 btn-add ml-2 text-sm text-primary add-rows cursor-pointer', $disabledAdd ? 'disabled' : ''),
- on::click('addRow(event)'),
setData('canAddRows', $canAddRows),
setData('fieldsCount', count($fields)),
set::title(sprintf($lang->thinkrun->tips->add, $canAddRows)),
@@ -130,7 +129,6 @@ class thinkTableInput extends thinkQuestion
(
'plus',
setClass('mr-1 btn-add ml-2 text-sm text-primary add-rows', $disabledAdd ? 'disabled' : ''),
- on::click('addRow(event)'),
setData('canAddRows', $canAddRows),
setData('fieldsCount', count($fields)),
set::title(sprintf($lang->thinkrun->tips->add, $canAddRows)),
@@ -178,7 +176,6 @@ class thinkTableInput extends thinkQuestion
(
'plus',
setClass('mr-1 btn-add ml-2 text-sm text-primary add-rows cursor-pointer'),
- on::click('addRow(event)'),
setData('canAddRows', $canAddRows),
setData('fieldsCount', count($fields)),
set::title(sprintf($lang->thinkrun->tips->add, $canAddRows)),
diff --git a/lib/zin/wg/visionswitcher/v1.php b/lib/zin/wg/visionswitcher/v1.php
index 5e7df5e07b..1c53c1d1b6 100644
--- a/lib/zin/wg/visionswitcher/v1.php
+++ b/lib/zin/wg/visionswitcher/v1.php
@@ -77,6 +77,11 @@ class visionSwitcher extends wg
$userVisions = array_filter(explode(',', $user->visions));
$configVisions = array_filter(explode(',', trim($config->visions, ',')));
+ pageJS(<< '{$user->visions}'.split(',');
+ window.getCurrentVision = () => '{$currentVision}';
+ JS);
+
/* The standalone lite version removes the lite interface button */
if(trim($config->visions, ',') == 'lite') return;
@@ -111,11 +116,6 @@ class visionSwitcher extends wg
);
}
- pageJS(<< '{$user->visions}'.split(',');
- window.getCurrentVision = () => '{$currentVision}';
- JS);
-
$dropdown = new dropdown
(
new btn
diff --git a/module/action/config.php b/module/action/config.php
index 494f26f090..89c7291629 100755
--- a/module/action/config.php
+++ b/module/action/config.php
@@ -1,5 +1,6 @@
action->objectNameFields['product'] = 'name';
+$config->action->objectNameFields['productline'] = 'name';
$config->action->objectNameFields['epic'] = 'title';
$config->action->objectNameFields['story'] = 'title';
$config->action->objectNameFields['requirement'] = 'title';
@@ -85,7 +86,7 @@ $config->action->majorList['doc'] = array('releaseddoc');
$config->action->needGetProjectType = 'build,task,bug,case,testcase,caselib,testtask,testsuite,testreport,doc,issue,release,risk,design,opportunity,trainplan,gapanalysis,researchplan,researchreport,';
$config->action->needGetRelateField = ',branch,story,epic,requirement,productplan,release,task,build,bug,testcase,case,testtask,testreport,doc,doclib,issue,risk,opportunity,trainplan,gapanalysis,team,whitelist,researchplan,researchreport,meeting,kanbanlane,kanbancolumn,module,review,';
-$config->action->noLinkModules = ',doclib,module,webhook,gitlab,instance,gitea,gogs,sonarqube,pipeline,jenkins,kanban,kanbanspace,kanbancolumn,kanbanlane,kanbanregion,kanbancard,execution,project,traincategory,apistruct,program,product,user,entry,repo,pivot,scene,boardspace,auditplan,auditresult,';
+$config->action->noLinkModules = ',doclib,module,webhook,gitlab,instance,gitea,gogs,sonarqube,pipeline,jenkins,kanban,kanbanspace,kanbancolumn,kanbanlane,kanbanregion,kanbancard,execution,project,traincategory,apistruct,program,product,user,entry,repo,pivot,scene,boardspace,auditplan,auditresult,productline,';
$config->action->ignoreObjectType4Dynamic = 'kanbanregion,kanbanlane,kanbancolumn';
$config->action->ignoreActions4Dynamic = 'disconnectxuanxuan,reconnectxuanxuan,loginxuanxuan,logoutxuanxuan,editmr,removemr';
@@ -94,7 +95,7 @@ $config->action->latestDateList = array('today', 'yesterday', 'thisWeek', 'lastW
$config->action->preferredTypeNum = 10;
$config->action->preferredType = new stdclass();
-$config->action->preferredType->ALM = array('user', 'story', 'task', 'bug', 'case', 'board', 'boardspace', 'doc', 'program', 'product', 'project', 'execution');
+$config->action->preferredType->ALM = array('user', 'story', 'task', 'bug', 'case', 'board', 'boardspace', 'doc', 'program', 'product', 'productline', 'project', 'execution');
$config->action->preferredType->light = array('user', 'story', 'task', 'bug', 'case', 'board', 'boardspace', 'doc', 'product', 'project', 'execution');
global $app, $lang;
diff --git a/module/action/lang/de.php b/module/action/lang/de.php
index 91f7d1b0a1..fdedd64672 100644
--- a/module/action/lang/de.php
+++ b/module/action/lang/de.php
@@ -187,6 +187,7 @@ $lang->action->objectTypes['metric'] = 'Metric';
$lang->action->objectTypes['projectbuild'] = 'Build';
$lang->action->objectTypes['board'] = 'Board';
$lang->action->objectTypes['boardspace'] = 'Board Space';
+$lang->action->objectTypes['productline'] = 'Product Line';
/* Used to describe operation history. */
$lang->action->desc = new stdclass();
diff --git a/module/action/lang/en.php b/module/action/lang/en.php
index c4661d0ee6..65a77885ea 100755
--- a/module/action/lang/en.php
+++ b/module/action/lang/en.php
@@ -187,6 +187,7 @@ $lang->action->objectTypes['metric'] = 'Metric';
$lang->action->objectTypes['projectbuild'] = 'Build';
$lang->action->objectTypes['board'] = 'Board';
$lang->action->objectTypes['boardspace'] = 'Board Space';
+$lang->action->objectTypes['productline'] = 'Product Line';
/* Used to describe operation history. */
$lang->action->desc = new stdclass();
diff --git a/module/action/lang/fr.php b/module/action/lang/fr.php
index b763fd0cce..ff68685f44 100644
--- a/module/action/lang/fr.php
+++ b/module/action/lang/fr.php
@@ -187,6 +187,7 @@ $lang->action->objectTypes['metric'] = 'Metric';
$lang->action->objectTypes['projectbuild'] = 'Build';
$lang->action->objectTypes['board'] = 'Board';
$lang->action->objectTypes['boardspace'] = 'Board Space';
+$lang->action->objectTypes['productline'] = 'Product Line';
/* Used to describe operation history. */
$lang->action->desc = new stdclass();
diff --git a/module/action/lang/zh-cn.php b/module/action/lang/zh-cn.php
index ddd2a93ccc..09f2068aef 100755
--- a/module/action/lang/zh-cn.php
+++ b/module/action/lang/zh-cn.php
@@ -187,6 +187,7 @@ $lang->action->objectTypes['metric'] = '度量';
$lang->action->objectTypes['projectbuild'] = '版本';
$lang->action->objectTypes['board'] = '白板';
$lang->action->objectTypes['boardspace'] = '白板空间';
+$lang->action->objectTypes['productline'] = '产品线';
/* 用来描述操作历史记录。*/
$lang->action->desc = new stdclass();
diff --git a/module/bi/config.php b/module/bi/config.php
index 811abf82ff..0cc499d968 100644
--- a/module/bi/config.php
+++ b/module/bi/config.php
@@ -14,6 +14,8 @@ $config->bi->conditionList['NOT IN'] = 'NOT IN';
$config->bi->conditionList['IS NOT NULL'] = 'IS NOT NULL';
$config->bi->conditionList['IS NULL'] = 'IS NULL';
+$config->bi->duckdbExcludeTables = array('metriclib', 'repofiles', 'repohistory', 'queue', 'duckdbqueue', 'action');
+
$config->bi->builtin = new stdclass();
$config->bi->builtin->modules = new stdclass();
$config->bi->builtin->screens = array(1, 2, 3, 4, 5, 6, 7, 8,1001);
diff --git a/module/bi/config/pivots.php b/module/bi/config/pivots.php
index 8dfafacb13..4dfd3050c0 100644
--- a/module/bi/config/pivots.php
+++ b/module/bi/config/pivots.php
@@ -2605,6 +2605,7 @@ and t1.resolution!=''
and (case when \$startDate='' then 1 else cast(t1.resolvedDate as date)>=cast(\$startDate as date) end)
and (case when \$endDate='' then 1 else cast(t1.resolvedDate as date)<=cast(\$endDate as date) end)
and (case when \$product = '' then 1 else t1.product=\$product end)
+and not (\$product='' and \$startDate='' and \$endDate='')
EOT,
'settings' => array
(
diff --git a/module/bi/control.php b/module/bi/control.php
index 8a40adf689..18f2a8fa18 100644
--- a/module/bi/control.php
+++ b/module/bi/control.php
@@ -35,6 +35,22 @@ class bi extends control
echo 'success';
}
+ /**
+ * Init parquet.
+ *
+ * @access public
+ * @return void
+ */
+ public function initParquet()
+ {
+ $startTime = microtime(true);
+ $this->bi->initParquet();
+ $endTime = microtime(true);
+ $runTime = $endTime - $startTime;
+ echo "$runTime \n";
+ echo 'success';
+ }
+
/**
* Ajax: get object options.
*
diff --git a/module/bi/model.php b/module/bi/model.php
index 1aa95357ed..78954606e3 100644
--- a/module/bi/model.php
+++ b/module/bi/model.php
@@ -1127,6 +1127,86 @@ class biModel extends model
return $duckdbTmpPath;
}
+ /**
+ * Get sql by month.
+ *
+ * @param string $month
+ * @access public
+ * @return array
+ */
+ public function getSqlByMonth($year = 'Y', $month = 'm')
+ {
+ $sqls = array();
+ $prefix = $this->config->db->prefix;
+ $year = date($year);
+ $month = date($month);
+
+ $begin = date("{$year}-{$month}-01 00:00:00");
+ $end = date("{$year}-{$month}-t 23:59:59", strtotime("$year-$month-01"));
+ $sqls[$prefix . "action_{$year}_{$month}"] = "select * from zt_action where date >= TIMESTAMP '$begin' and date <= TIMESTAMP '$end'";
+
+ return $sqls;
+ }
+
+ /**
+ * Get action sync sql.
+ *
+ * @param string $range
+ * @access public
+ * @return array
+ */
+ public function getActionSyncSql($range = 'current')
+ {
+ if($range == 'current') return $this->getSqlByMonth();
+
+ $actionDate = $this->biTao->fetchActionDate();
+ $begin = new DateTime($actionDate->minDate);
+ $end = new DateTime($actionDate->maxDate);
+
+ $sqls = array();
+ while($begin <= $end)
+ {
+ $year = $begin->format('Y');
+ $month = $begin->format('m');
+ $sqls += $this->getSqlByMonth($year, $month);
+ $begin->modify('+1 month');
+ }
+
+ return $sqls;
+ }
+
+ /**
+ * Init parquet.
+ *
+ * @access public
+ * @return void
+ */
+ public function initParquet()
+ {
+ $duckdb = $this->getDuckDBPath();
+ if(!$duckdb) return $this->lang->bi->binNotExists;
+
+ $duckdbTmpPath = $this->getDuckDBTmpDir();
+ if(!$duckdbTmpPath) return sprintf($this->lang->bi->tmpPermissionDenied, $this->getDuckDBTmpDir(true), $this->getDuckDBTmpDir(true));
+
+ $tables = $this->biTao->fetchAllTables();
+ $copySQLs = array();
+ foreach($tables as $table) $copySQLs[] = "copy (select * from {$table}) to '{$duckdbTmpPath}{$table}.parquet'";
+
+ $date = date("Y-m-01 00:00:00");
+ $prefix = $this->config->db->prefix;
+
+ $copySQLs[] = "copy (select * from {$prefix}action where date < TIMESTAMP '$date') to '{$duckdbTmpPath}{$prefix}action_" . date('Y_m', strtotime('-1 month')) . ".parquet'";
+
+ $copySQL = implode(';', $copySQLs);
+ if(empty($copySQL)) return true;
+
+ $command = $this->prepareSyncCommand($duckdb->bin, $duckdb->extension, $copySQL);
+ $output = shell_exec($command);
+ $this->saveLogs("Sync command: $command");
+ return $output;
+ }
+
/**
* 准备同步数据库所需的复制SQL。
* Prepare copy SQL for sync.
@@ -1137,26 +1217,17 @@ class biModel extends model
*/
public function prepareCopySQL($duckdbTmpPath)
{
- $duckdbQueue = $this->dao->select('*')->from(TABLE_DUCKDBQUEUE)
- ->where('updatedTime >= syncTime')
- ->orWhere('syncTime IS NULL')
- ->fetchAll('object');
+ $tables = $this->biTao->fetchTableQueue();
- if(empty($duckdbQueue)) return '';
+ if(empty($tables)) return '';
- $tables = array_keys($duckdbQueue);
+ $copySQLs = array();
+ foreach($tables as $table) $copySQLs[] = "copy (select * from {$table}) to '{$duckdbTmpPath}{$table}.parquet'";
- $copySQLs = array();
- foreach($tables as $table)
- {
- $sql = "select * from {$table}";
- $copySQLs[] = "copy ($sql) to '{$duckdbTmpPath}{$table}.parquet'";
- }
+ $actions = $this->getActionSyncSql();
+ foreach($actions as $table => $sql) $copySQLs[] = "copy ({$sql}) to '{$duckdbTmpPath}{$table}.parquet'";
- $this->dao->update(TABLE_DUCKDBQUEUE)
- ->set('syncTime')->eq(helper::now())
- ->where('object')->in($tables)
- ->exec();
+ $this->biTao->updateSyncTime($tables);
return implode(';', $copySQLs);
}
@@ -1265,8 +1336,9 @@ class biModel extends model
if(empty($filter['default'])) continue;
if(!isset($filter['from']) || $filter['from'] != 'query') continue;
- $filters[$index]['default'] = $this->loadModel('pivot')->processDateVar($filter['default']);
- if($filters[$index]['type'] == 'datetime') $filters[$index]['default'] .= ':00.000000000';
+ if($filter['type'] == 'date' || $filter['type'] == 'datetime') $filters[$index]['default'] = $this->loadModel('pivot')->processDateVar($filter['default']);
+ if($filter['type'] == 'datetime') $filters[$index]['default'] .= ':00.000000000';
+ if($filter['type'] == 'multipleselect' && is_array($filter['default'])) $filters[$index]['default'] = implode("','", $filter['default']);
if($emptyValue) $filters[$index]['default'] = '';
}
@@ -1283,12 +1355,16 @@ class biModel extends model
* @access public
* @return object
*/
- public function sql2Statement($sql)
+ public function sql2Statement($sql, $mode = 'text')
{
$this->app->loadClass('sqlparser', true);
$parser = new sqlparser($sql);
- if($parser->statementsCount == 0) return $this->lang->dataview->empty;
+ if($parser->statementsCount == 0)
+ {
+ if($mode == 'builder') return $this->lang->dataview->emptyBuilder;
+ return $this->lang->dataview->empty;
+ }
if($parser->statementsCount > 1) return $this->lang->dataview->onlyOne;
if(!$parser->isSelect) return $this->lang->dataview->allowSelect;
@@ -1594,7 +1670,7 @@ class biModel extends model
$stateObj->beforeQuerySql();
- $statement = $this->sql2Statement($sql);
+ $statement = $this->sql2Statement($sql, $stateObj->mode);
if(is_string($statement)) return $stateObj->setError($statement);
$checked = $this->validateSql($sql, $driver);
@@ -1641,6 +1717,7 @@ class biModel extends model
public function getTableList()
{
$originTableTreeMenu = $this->loadModel('dataview')->getOriginTreeMenu();
+ $dataviewTreeMenu = $this->loadModel('tree')->getGroupTree(0, 'dataview');
$tableList = array();
foreach($originTableTreeMenu as $menu)
@@ -1652,11 +1729,26 @@ class biModel extends model
if(!is_array($item))
{
$text = $item->key == 'story' ? $this->lang->story->common : $item->text;
- $tableList[$item->key] = $text;
+ $tableList[$this->config->db->prefix . $item->key] = $text;
continue;
}
- foreach($item->items as $subItem) $tableList[$subItem->key] = $subItem->text;
+ foreach($item->items as $subItem) $tableList[$this->config->db->prefix . $subItem->key] = $subItem->text;
+ }
+ }
+ foreach($dataviewTreeMenu as $menu)
+ {
+ if(empty($menu->items)) continue;
+
+ foreach($menu->items as $item)
+ {
+ if(!is_array($item))
+ {
+ $tableList['ztv_' . $item->key] = $item->text;
+ continue;
+ }
+
+ foreach($item->items as $subItem) $tableList['ztv_' . $subItem->key] = $subItem->text;
}
}
diff --git a/module/bi/tao.php b/module/bi/tao.php
new file mode 100644
index 0000000000..c7a9346059
--- /dev/null
+++ b/module/bi/tao.php
@@ -0,0 +1,74 @@
+config->db->prefix;
+ $excludes = $this->config->bi->duckdbExcludeTables;
+ foreach($excludes as $index => $table) $excludes[$index] = $prefix . $table;
+
+ return $this->dao->select("table_name as 'table'")
+ ->from('information_schema.tables')
+ ->where('table_type')->eq('BASE TABLE')
+ ->andWhere('table_schema')->eq($this->config->db->name)
+ ->andWhere('table_name')->notin($excludes)
+ ->fetchPairs();
+ }
+
+ /**
+ * Fetch table queue.
+ *
+ * @access protected
+ * @return array
+ */
+ protected function fetchTableQueue()
+ {
+ $prefix = $this->config->db->prefix;
+ $excludes = $this->config->bi->duckdbExcludeTables;
+ foreach($excludes as $index => $table) $excludes[$index] = $prefix . $table;
+
+ return $this->dao->select('object')->from(TABLE_DUCKDBQUEUE)
+ ->where('object')->notin($excludes)
+ ->andWhere('updatedTime >= syncTime', true)
+ ->orWhere('syncTime IS NULL')
+ ->markRight(1)
+ ->fetchPairs();
+ }
+
+ /**
+ * Update sync time.
+ *
+ * @param array $tables
+ * @access protected
+ * @return void
+ */
+ protected function updateSyncTime($tables)
+ {
+ $this->dao->update(TABLE_DUCKDBQUEUE)
+ ->set('syncTime')->eq(helper::now())
+ ->where('object')->in($tables)
+ ->exec();
+ }
+
+ /**
+ * Fetch action date.
+ *
+ * @access protected
+ * @return object
+ */
+ protected function fetchActionDate()
+ {
+ return $this->dao->select('min(date) as minDate, max(date) as maxDate')
+ ->from(TABLE_ACTION)
+ ->where('date')->ge('2009-01-01')
+ ->fetch();
+ }
+
+}
diff --git a/module/block/lang/de.php b/module/block/lang/de.php
index 27f02d714d..ca345e8594 100644
--- a/module/block/lang/de.php
+++ b/module/block/lang/de.php
@@ -95,7 +95,7 @@ $lang->block->confirmRemoveBlock = 'Möchten Sie den Block löschen?';
$lang->block->noticeNewBlock = 'ZenTao 10.+ hat neue Layouts für jeden View. Möchten Sie die neue Ansicht nutzen?';
$lang->block->confirmReset = 'Möchten Sie das Dashboard zurücksetzen?';
$lang->block->closeForever = 'Dauerhaft schließen';
-$lang->block->confirmClose = 'Möchten Sie den Block dauerhaft schlißen? Nach der Ausführung ist der Block nicht mehr verfügbar. Er kann unter Admin->Custom aber wieder aktiviert werden.';
+$lang->block->confirmClose = 'Möchten Sie den Block dauerhaft schlißen? Nach der Ausführung ist der Block nicht mehr verfügbar. Er kann unter Admin->Feature->My->Block aber wieder aktiviert werden.';
$lang->block->remove = 'Entfernen';
$lang->block->refresh = 'Aktualisieren';
$lang->block->nbsp = '';
diff --git a/module/block/lang/en.php b/module/block/lang/en.php
index abb49eabd6..3da7540ab3 100644
--- a/module/block/lang/en.php
+++ b/module/block/lang/en.php
@@ -95,7 +95,7 @@ $lang->block->confirmRemoveBlock = 'Do you want to remove the Block?';
$lang->block->noticeNewBlock = 'A new layout is available. Do you want to switch to the new one?';
$lang->block->confirmReset = 'Do you want to reset the layout?';
$lang->block->closeForever = 'Permanent Close';
-$lang->block->confirmClose = 'Do you want to permanently close this block? Once done, it is not available to anyone. It can be activiated at Admin->Custom.';
+$lang->block->confirmClose = 'Do you want to permanently close this block? Once done, it is not available to anyone. It can be activiated at Admin->Feature->My->Block.';
$lang->block->remove = 'Remove';
$lang->block->refresh = 'Refresh';
$lang->block->nbsp = ' ';
diff --git a/module/block/lang/zh-cn.php b/module/block/lang/zh-cn.php
index d583082625..6669e19479 100644
--- a/module/block/lang/zh-cn.php
+++ b/module/block/lang/zh-cn.php
@@ -95,7 +95,7 @@ $lang->block->confirmRemoveBlock = '确定隐藏区块吗?';
$lang->block->noticeNewBlock = '10.0版本以后各个视图主页提供了全新的视图,您要启用新的视图布局吗?';
$lang->block->confirmReset = '是否恢复默认布局?';
$lang->block->closeForever = '永久关闭';
-$lang->block->confirmClose = '确定永久关闭该区块吗?关闭后所有人都将无法使用该区块,可以在后台自定义中打开。';
+$lang->block->confirmClose = '确定永久关闭该区块吗?关闭后所有人都将无法使用该区块,可以在[后台-功能配置-地盘-区块]中打开。';
$lang->block->remove = '移除';
$lang->block->refresh = '刷新';
$lang->block->nbsp = '';
diff --git a/module/block/ui/systemmode.html.php b/module/block/ui/systemmode.html.php
index 1ea3a1fca2..b89fed864f 100644
--- a/module/block/ui/systemmode.html.php
+++ b/module/block/ui/systemmode.html.php
@@ -36,7 +36,7 @@ function printSystemMode()
div
(
set('class', 'px-4 pb-2'),
- div(set('class', 'pb-2'), span(set('class', 'font-bold'), $modeName)),
+ div(set('class', 'pb-2'), span(set('class', 'font-bold text-black'), $modeName)),
span(set('class', 'text-sm text-gray'), $lang->block->customModeTip->{$mode})
)
),
diff --git a/module/block/ui/waterfallganttblock.html.php b/module/block/ui/waterfallganttblock.html.php
index 38993c5a19..058d3be11a 100644
--- a/module/block/ui/waterfallganttblock.html.php
+++ b/module/block/ui/waterfallganttblock.html.php
@@ -19,7 +19,7 @@ $productItems = array();
foreach($products as $id => $productName)
{
$url = createLink('block', 'printBlock', "blockID={$block->id}¶ms=" . helper::safe64Encode("module={$block->module}&productID={$id}"));
- $productItems[] = array('text' => $productName, 'data-url' => $url, 'data-on' => 'click', 'data-do' => "loadBlock('$block->id', options.url)");
+ $productItems[] = array('text' => $productName, 'data-url' => $url, 'active' => $productID == $id, 'data-on' => 'click', 'data-do' => "loadBlock('$block->id', options.url)");
}
panel
(
diff --git a/module/block/zen.php b/module/block/zen.php
index 4c6e173b99..244ae20593 100644
--- a/module/block/zen.php
+++ b/module/block/zen.php
@@ -405,35 +405,12 @@ class blockZen extends block
$welcomeType = '19:00';
foreach($this->lang->block->welcomeList as $type => $name) $welcomeType = $time >= $type ? $type : $welcomeType;
- /* 获取禅道陪伴当前用户总天数。 */
- if(!empty($this->config->installedDate))
- {
- $firstUseDate = $this->config->global->installedDate;
- }
- else
- {
- $firstUseDate = $this->dao->select('date')->from(TABLE_ACTION)
- ->where('date')->gt('1971-01-01')
- ->andWhere('actor')->eq($this->app->user->account)
- ->orderBy('date_asc')
- ->limit('1')
- ->fetch('date');
- }
-
- if($firstUseDate)
- {
- $usageDays = '';
- $usageDateInfo = helper::getDateInterval($firstUseDate);
- if(!empty($usageDateInfo->year)) $usageDays .= $usageDateInfo->year . ' ' . $this->lang->year . ' ';
- if(!empty($usageDateInfo->month)) $usageDays .= $usageDateInfo->month . ' ' . $this->lang->month . ' ';
- if(!empty($usageDateInfo->day)) $usageDays .= $usageDateInfo->day . ' ' . $this->lang->day . ' ';
-
- if(!$usageDays) $usageDays .= "0 {$this->lang->day}";
- }
- else
- {
- $usageDays = ' 1 ' . $this->lang->day; // 最小陪伴天数是一天。
- }
+ $usageDays = '';
+ $dateUsed = $this->loadModel('admin')->genDateUsed();
+ if(!empty($dateUsed->year)) $usageDays .= $dateUsed->year . ' ' . $this->lang->year . ' ';
+ if(!empty($dateUsed->month)) $usageDays .= $dateUsed->month . ' ' . $this->lang->month . ' ';
+ if(!empty($dateUsed->day)) $usageDays .= $dateUsed->day . ' ' . $this->lang->day . ' ';
+ if(!$usageDays) $usageDays = "0 {$this->lang->day}";
if(strpos($this->app->getClientLang(), 'zh') !== false) $usageDays = str_replace(' ', '', $usageDays);
$yesterday = strtotime("-1 day");
diff --git a/module/branch/model.php b/module/branch/model.php
index 4a2371a5a4..639cb13f3f 100644
--- a/module/branch/model.php
+++ b/module/branch/model.php
@@ -316,7 +316,11 @@ class branchModel extends model
->where('id')->eq($branchID)
->exec();
- if(dao::isError()) dao::$errors[] = 'branch#' . ($index + 1) . dao::getError(true);
+ if(dao::isError())
+ {
+ dao::$errors["name[$index]"] = dao::getError(true);
+ return false;
+ }
$changes[$branchID] = common::createChanges($oldBranchList[$branchID], $branch);
}
diff --git a/module/branch/test/lib/batcheditbranch.ui.class.php b/module/branch/test/lib/batcheditbranch.ui.class.php
new file mode 100644
index 0000000000..84eac375d8
--- /dev/null
+++ b/module/branch/test/lib/batcheditbranch.ui.class.php
@@ -0,0 +1,54 @@
+initForm('branch', 'manage', $productID, 'appIframe-product');
+ $form->dom->allTab->click();
+ $form->wait(1);
+ $form->dom->selectAllBtn->click();//全选分支
+ $form->dom->batchEditBtn->click();//点击编辑按钮
+ $form->wait(2);
+ $secID = $form->dom->id_static_1->getText();//获取第二个ID
+ $nameDom = "name[{$secID}]";
+ $descDom = "desc[{$secID}]";
+ $tipDom = "name[{$secID}]Tip";
+ //设置表单字段
+ if (isset($editBranch->name)) $form->dom->$nameDom->setValue($editBranch->name);
+ if (isset($editBranch->desc)) $form->dom->$descDom->setValue($editBranch->desc);
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(2);
+ //判断批量编辑结果
+ if ($form->dom->allTab === false)
+ {
+ $nameTip = $form->dom->$tipDom->getText();
+ $nameEmptyTip = sprintf($this->lang->error->notempty, $this->lang->branch->name);
+ if ($nameTip === $nameEmptyTip) return $this->success('分支名称必填提示信息正确');
+ if ($editBranch->name != '' && $form->dom->$tipDom)
+ {
+ $nameExistTip = str_replace('@branch@', $this->lang->branch->common, $this->lang->branch->existName);
+ return ($nameTip === $nameExistTip)
+ ? $this->success('分支已存在提示信息正确')
+ : $this->failed('分支已存在提示信息不正确');
+ }
+ return $this->failed('分支名称必填提示信息不正确');
+ }
+ else
+ {
+ $branchName = $form->dom->secName->getText();
+ $branchDesc = $form->dom->secDesc->getText();
+ return ($branchName === $editBranch->name && $branchDesc === $editBranch->desc)
+ ? $this->success('批量编辑分支成功')
+ : $this->failed('批量编辑分支失败');
+ }
+ }
+}
diff --git a/module/branch/test/lib/createbranch.ui.class.php b/module/branch/test/lib/createbranch.ui.class.php
new file mode 100755
index 0000000000..c734897fd2
--- /dev/null
+++ b/module/branch/test/lib/createbranch.ui.class.php
@@ -0,0 +1,39 @@
+initForm('branch', 'manage', $productID, 'appIframe-product');
+ $form->dom->btn($this->lang->branch->createAction)->click();
+ $form->waitElement($form->dom->branchName);
+ //设置表单字段值
+ if (isset($branch->name)) $form->dom->branchName->setValue($branch->name);
+ if (isset($branch->desc)) $form->dom->branchDesc->setValue($branch->desc);
+ $form->dom->save->click();
+ $form->wait(2);
+ if ($form->dom->createBranchForm)
+ {
+ if ($this->checkFormTips('branch')) return $this->success('分支名称必填提示信息正确');
+ if ($branch->name != '' && $form->dom->nameTip)
+ {
+ //分支已存在
+ $nameTip = str_replace('@branch@', $this->lang->branch->common, $this->lang->branch->existName);
+ return ($form->dom->nameTip->getText() == $nameTip)
+ ? $this->success('分支已存在提示信息正确')
+ : $this->failed('分支已存在提示信息不正确');
+ }
+ return $this->failed('分支名称必填提示信息不正确');
+ }
+ return $this->success('创建分支成功');
+ }
+}
diff --git a/module/branch/test/lib/editbranch.ui.class.php b/module/branch/test/lib/editbranch.ui.class.php
new file mode 100644
index 0000000000..cc03edd72b
--- /dev/null
+++ b/module/branch/test/lib/editbranch.ui.class.php
@@ -0,0 +1,41 @@
+initForm('branch', 'manage', $productID, 'appIframe-product');
+ $form->dom->allTab->click();
+ $form->dom->editBtn->click();
+ //设置表单字段值
+ if (isset($editBranch->name)) $form->dom->editName->setValue($editBranch->name);
+ if (isset($editBranch->desc)) $form->dom->editDesc->setValue($editBranch->desc);
+ $form->dom->editSave->click();
+ $form->wait(2);
+ if ($form->dom->zin_branch_edit_1_form)
+ {
+ if ($this->checkFormTips('branch')) return $this->success('分支名称必填提示信息正确');
+ if (isset($editBranch->name) && ($form->dom->nameTip))
+ {
+ //分支已存在
+ $nameTip = str_replace('@branch@', $this->lang->branch->common, $this->lang->branch->existName);
+ return ($form->dom->nameTip->getText() == $nameTip)
+ ? $this->success('分支已存在提示信息正确')
+ : $this->failed('分支已存在提示信息不正确');
+ }
+ return $this->failed('分支名称必填提示信息不正确');
+ }
+ return ($form->dom->secName->getText() == $editBranch->name)
+ ? $this->success('编辑分支成功')
+ : $this->failed('编辑分支失败');
+ }
+}
diff --git a/module/branch/test/ui/batcheditbranch.php b/module/branch/test/ui/batcheditbranch.php
new file mode 100755
index 0000000000..6b342949a4
--- /dev/null
+++ b/module/branch/test/ui/batcheditbranch.php
@@ -0,0 +1,52 @@
+#!/usr/bin/env php
+id->range('11');
+$product->name->range('多分支产品');
+$product->status->range('normal');
+$product->type->range('branch');
+$product->gen(1);
+
+$branch = zenData('branch');
+$branch->id->range('1-2');
+$branch->product->range('11');
+$branch->name->range('分支01,分支02');
+$branch->desc->range('分支描述01,分支描述02');
+$branch->gen(2);
+
+$tester = new batchEditBranchTester();
+$tester->login();
+
+$productID['productID'] = 11;
+$editBranch = new stdClass();
+$editBranch->name = '';
+r($tester->batchEditBranch($editBranch, $productID)) && p('message,status') && e('分支名称必填提示信息正确,SUCCESS');
+
+$editBranch->name = '分支02';
+r($tester->batchEditBranch($editBranch, $productID)) && p('message,status') && e('分支已存在提示信息正确,SUCCESS');
+
+$editBranch->name = '分支test编辑';
+$editBranch->desc = '这是一行分支的描述';
+r($tester->batchEditBranch($editBranch, $productID)) && p('message,status') && e('批量编辑分支成功,SUCCESS');
+
+$tester->closeBrowser();
diff --git a/module/branch/test/ui/createbranch.php b/module/branch/test/ui/createbranch.php
new file mode 100755
index 0000000000..50d8267407
--- /dev/null
+++ b/module/branch/test/ui/createbranch.php
@@ -0,0 +1,42 @@
+#!/usr/bin/env php
+id->range('11');
+$product->name->range('多分支产品');
+$product->status->range('normal');
+$product->type->range('branch');
+$product->gen(1);
+zendata('branch')->loadYaml('branch', false, 2)->gen(0);
+$tester = new createBranchTester();
+$tester->login();
+
+$productID['productID'] = 11;
+$branch = new stdClass();
+$branch->name = '';
+r($tester->createBranch($branch, $productID)) && p('message,status') && e('分支名称必填提示信息正确,SUCCESS');
+
+$branch->name = '分支test';
+$branch->desc = '这是一行分支的描述';
+r($tester->createBranch($branch, $productID)) && p('message,status') && e('创建分支成功,SUCCESS');
+
+r($tester->createBranch($branch, $productID)) && p('message,status') && e('分支已存在提示信息正确,SUCCESS');
+$tester->closeBrowser();
diff --git a/module/branch/test/ui/editbranch.php b/module/branch/test/ui/editbranch.php
new file mode 100755
index 0000000000..34aff1460f
--- /dev/null
+++ b/module/branch/test/ui/editbranch.php
@@ -0,0 +1,52 @@
+#!/usr/bin/env php
+id->range('11');
+$product->name->range('多分支产品');
+$product->status->range('normal');
+$product->type->range('branch');
+$product->gen(1);
+
+$branch = zenData('branch');
+$branch->id->range('1-2');
+$branch->product->range('11');
+$branch->name->range('分支01,分支02');
+$branch->desc->range('分支描述01,分支描述02');
+$branch->gen(2);
+
+$tester = new editBranchTester();
+$tester->login();
+
+$productID['productID'] = 11;
+$editBranch = new stdClass();
+$editBranch->name = '';
+r($tester->editBranch($editBranch, $productID)) && p('message,status') && e('分支名称必填提示信息正确,SUCCESS');
+
+$editBranch->name = '分支02';
+r($tester->editBranch($editBranch, $productID)) && p('message,status') && e('分支已存在提示信息正确,SUCCESS');
+
+$editBranch->name = '分支test编辑';
+$editBranch->desc = '这是一行分支的描述';
+r($tester->editBranch($editBranch, $productID)) && p('message,status') && e('编辑分支成功,SUCCESS');
+
+$tester->closeBrowser();
diff --git a/module/branch/test/ui/page/manage.php b/module/branch/test/ui/page/manage.php
new file mode 100755
index 0000000000..b2cb59c365
--- /dev/null
+++ b/module/branch/test/ui/page/manage.php
@@ -0,0 +1,31 @@
+ "//*[@id='zin_branch_create_form']/div[1]/input",
+ 'branchDesc' => "//*[@id='zin_branch_create_form']/div[2]/textarea",
+ 'save' => "//*[@id='zin_branch_create_form']/div[3]/div/button",
+ /*分支列表*/
+ 'allTab' => "//*[@id='featureBar']/menu/li[1]/a",
+ 'activeTab' => "//*[@id='featureBar']/menu/li[2]/a",
+ 'closedTab' => "//*[@id='featureBar']/menu/li[3]/a",
+ 'secName' => "//*[@id='table-branch-manage']/div[2]/div[1]/div/div[4]/div",
+ 'secDesc' => "//*[@id='table-branch-manage']/div[2]/div[2]/div/div[8]/div",
+ 'secStatus' => "//*[@id='table-branch-manage']/div[2]/div[2]/div/div[5]/div/span",
+ 'selectAllBtn' => "//*[@id='table-branch-manage']/div[3]/div[1]/div/label",
+ 'batchEditBtn' => "//*[@id='table-branch-manage']/div[3]/nav[1]/button[1]",
+ 'editBtn' => "//*[@id='table-branch-manage']/div[2]/div[3]/div/div[2]/div/nav/a[1]",
+ 'closeBtn' => "//*[@id='table-branch-manage']/div[2]/div[3]/div/div[2]/div/nav/a[2]",
+ 'activateBtn' => "//*[@id='table-branch-manage']/div[2]/div[3]/div/div[2]/div/nav/a[2]",
+ /*编辑分支页*/
+ 'editName' => "//*[@id='zin_branch_edit_1_form']/div[1]/input",
+ 'editDesc' => "//*[@id='zin_branch_edit_1_form']/div[3]/textarea",
+ 'editSave' => "//*[@id='zin_branch_edit_1_form']/div[4]/div/button",
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/branch/ui/manage.html.php b/module/branch/ui/manage.html.php
index 9958f1ab24..fbb9ce9783 100644
--- a/module/branch/ui/manage.html.php
+++ b/module/branch/ui/manage.html.php
@@ -20,7 +20,7 @@ featureBar
$canCreate = hasPriv('branch', 'create');
$canBatchEdit = hasPriv('branch', 'batchEdit');
$canMerge = hasPriv('branch', 'mergeBranch');
-if($canCreate) $createItem = array('icon' => 'plus', 'class' => 'primary branch-create-btn', 'text' => $lang->branch->create, 'url' => $this->createLink('branch', 'create', "productID={$product->id}", '', true), 'data-toggle' => 'modal');
+if($canCreate) $createItem = array('icon' => 'plus', 'class' => 'primary branch-create-btn', 'text' => $lang->branch->create, 'url' => $this->createLink('branch', 'create', "productID={$product->id}"), 'data-toggle' => 'modal');
toolbar
(
!empty($createItem) ? item(set($createItem)) : null,
diff --git a/module/bug/js/browse.ui.js b/module/bug/js/browse.ui.js
index bb9aebffcc..e7ea66142d 100644
--- a/module/bug/js/browse.ui.js
+++ b/module/bug/js/browse.ui.js
@@ -16,6 +16,13 @@ $(document).off('click', '.batch-btn').on('click', '.batch-btn', function()
{
postAndLoadPage(url, form);
}
+}).off('click', '#actionBar .export-btn').on('click', '#actionBar export-btn', function()
+{
+ const dtable = zui.DTable.query($('#table-bug-browse'));
+ const checkedList = dtable ? dtable.$.getChecks() : [];
+ if(!checkedList.length) return;
+
+ $.cookie.set('checkedItem', checkedList, {expires:config.cookieLife, path:config.webRoot});
});
/**
diff --git a/module/bug/js/common.ui.js b/module/bug/js/common.ui.js
index 0e5c94b262..14124e74c4 100644
--- a/module/bug/js/common.ui.js
+++ b/module/bug/js/common.ui.js
@@ -34,7 +34,7 @@ function changeProduct(event)
loadProductBuilds(productID);
loadProductPlans(productID);
loadProductStories(productID, bug.storyID);
- if(config.currentMethod == 'edit' && edition == 'max') loadIdentify();
+ if(methodName == 'edit' && edition == 'max') loadIdentify();
}
}
@@ -59,7 +59,7 @@ function changeProject(event)
loadExecutionLabel(projectID);
loadExecutions(productID, projectID);
loadAssignedTo(productID, projectID);
- if(config.currentMethod == 'edit' && edition == 'max') loadIdentify();
+ if(methodName == 'edit' && edition == 'max') loadIdentify();
}
function changeExecution(event)
@@ -137,8 +137,8 @@ window.refreshExecutionBuild = function(event)
function loadProductBranches(productID)
{
- const branchStatus = config.currentMethod == 'create' ? 'active' : 'all';
- const oldBranch = config.currentMethod == 'edit' ? bug.branch : 0;
+ const branchStatus = methodName == 'create' ? 'active' : 'all';
+ const oldBranch = methodName == 'edit' ? bug.branch : 0;
let param = "productID=" + productID + "&oldBranch=" + oldBranch + "¶m=" + branchStatus;
if(typeof(tab) != 'undefined' && (tab == 'execution' || tab == 'project')) param += "&projectID=" + bug[tab];
$.getJSON($.createLink('branch', 'ajaxGetBranches', param), function(data)
@@ -155,7 +155,7 @@ function loadProductBranches(productID)
{
$('[name="product"]').closest('.input-group').append($('').picker({name: 'branch', items: data, defaultValue: data[0].value, required: true}));
}
- $('#branchPicker').css('width', config.currentMethod == 'create' ? '120px' : '65px');
+ $('#branchPicker').css('width', methodName == 'create' ? '120px' : '65px');
}
else
{
@@ -167,7 +167,7 @@ function loadProductBranches(productID)
function loadProductModules(productID)
{
- if(config.currentMethod == 'edit')
+ if(methodName == 'edit')
{
const moduleID = $('[name="module"]').val();
}
@@ -224,7 +224,7 @@ function loadExecutions(productID, projectID = 0)
function loadExecutionLabel(projectID)
{
- if(config.currentMethod == 'create' && projectID > 0)
+ if(methodName == 'create' && projectID > 0)
{
const link = $.createLink('bug', 'ajaxGetExecutionLang', 'projectID=' + projectID);
$.post(link, function(executionLang)
@@ -327,7 +327,7 @@ function loadProjectBuilds(projectID)
const productID = $('[name="product"]').val();
const oldOpenedBuild = $('[name^="openedBuild"]').val() ? $('[name^="openedBuild"]').val().toString() : 0;
- if(config.currentMethod == 'create')
+ if(methodName == 'create')
{
const link = $.createLink('build', 'ajaxGetProjectBuilds', 'projectID=' + projectID + '&productID=' + productID + '&varName=openedBuild&build=&branch=' + branch);
$.getJSON(link, function(data)
@@ -366,7 +366,7 @@ function loadProductBuilds(productID, type = 'normal', buildBox = 'all')
let branch = $('[name="branch"]').val();
if(typeof(branch) == 'undefined') branch = 0;
- if(config.currentMethod == 'create')
+ if(methodName == 'create')
{
if(buildBox == 'all' || buildBox == 'openedBuild')
{
@@ -420,7 +420,7 @@ function loadExecutionBuilds(executionID, num)
if(typeof(branch) == 'undefined') branch = 'all';
if(typeof(productID) == 'undefined') productID = 0;
- if(config.currentMethod == 'create')
+ if(methodName == 'create')
{
const link = $.createLink('build', 'ajaxGetExecutionBuilds', 'executionID=' + executionID + '&productID=' + productID + '&varName=openedBuild&build=' + oldOpenedBuild + "&branch=" + branch + "&needCreate=true");
$.getJSON(link, function(data)
@@ -666,7 +666,7 @@ function setBranchRelated(event)
function loadBuildActions()
{
- if(config.currentMethod == 'edit') return;
+ if(methodName == 'edit') return;
$('#createRelease, #createBuild').hide();
let itemCount = $('[name^=openedBuild]').zui('picker').options.items.length;
if(itemCount <= 1)
diff --git a/module/bug/lang/de.php b/module/bug/lang/de.php
index 5d465367c4..2b7991e57a 100644
--- a/module/bug/lang/de.php
+++ b/module/bug/lang/de.php
@@ -82,6 +82,7 @@ $lang->bug->task = 'Aufgabe';
$lang->bug->relatedBug = 'Verknüpfter Bug';
$lang->bug->case = 'Fall';
$lang->bug->linkMR = 'Related MRs';
+$lang->bug->linkPR = 'Related PRs';
$lang->bug->linkCommit = 'Related Commits';
$lang->bug->productplan = $lang->bug->plan;
$lang->bug->codeBranch = 'Code branch';
diff --git a/module/bug/lang/en.php b/module/bug/lang/en.php
index dccd2c6aa5..71587bb3b3 100644
--- a/module/bug/lang/en.php
+++ b/module/bug/lang/en.php
@@ -82,6 +82,7 @@ $lang->bug->task = 'Task';
$lang->bug->relatedBug = 'Related Bugs';
$lang->bug->case = 'Cases';
$lang->bug->linkMR = 'Related MRs';
+$lang->bug->linkPR = 'Related PRs';
$lang->bug->linkCommit = 'Related Commits';
$lang->bug->productplan = $lang->bug->plan;
$lang->bug->codeBranch = 'Code branch';
diff --git a/module/bug/lang/fr.php b/module/bug/lang/fr.php
index f59b71ac7f..c1054fdf23 100644
--- a/module/bug/lang/fr.php
+++ b/module/bug/lang/fr.php
@@ -82,6 +82,7 @@ $lang->bug->task = 'Tâche';
$lang->bug->relatedBug = 'Bugs Liés';
$lang->bug->case = 'CasTests';
$lang->bug->linkMR = 'Related MRs';
+$lang->bug->linkPR = 'Related PRs';
$lang->bug->linkCommit = 'Related Commits';
$lang->bug->productplan = $lang->bug->plan;
$lang->bug->codeBranch = 'Code branch';
diff --git a/module/bug/lang/zh-cn.php b/module/bug/lang/zh-cn.php
index 20c173e20b..0180cc5e5a 100644
--- a/module/bug/lang/zh-cn.php
+++ b/module/bug/lang/zh-cn.php
@@ -82,6 +82,7 @@ $lang->bug->task = '相关任务';
$lang->bug->relatedBug = '相关Bug';
$lang->bug->case = '相关用例';
$lang->bug->linkMR = '相关合并请求';
+$lang->bug->linkPR = '相关推送请求';
$lang->bug->linkCommit = '相关代码版本';
$lang->bug->productplan = $lang->bug->plan;
$lang->bug->codeBranch = '代码分支';
diff --git a/module/bug/model.php b/module/bug/model.php
index 45adca42bb..0365b18b7d 100644
--- a/module/bug/model.php
+++ b/module/bug/model.php
@@ -2158,8 +2158,8 @@ class bugModel extends model
{
return $this->dao->select('t1.revision,t3.id AS id,t3.title AS title')
->from(TABLE_REPOHISTORY)->alias('t1')
- ->leftJoin(TABLE_RELATION)->alias('t2')->on('t2.relation="completedin" AND t2.BType="commit" AND t2.BID=t1.id')
- ->leftJoin(TABLE_BUG)->alias('t3')->on('t2.AType="bug" AND t2.AID=t3.id')
+ ->leftJoin(TABLE_RELATION)->alias('t2')->on("t2.relation='completedin' AND t2.BType='commit' AND t2.BID=t1.id")
+ ->leftJoin(TABLE_BUG)->alias('t3')->on("t2.AType='bug' AND t2.AID=t3.id")
->where('t1.revision')->in($revisions)
->andWhere('t1.repo')->eq($repoID)
->andWhere('t3.id')->ne('')
diff --git a/module/bug/ui/create.html.php b/module/bug/ui/create.html.php
index 2a5c04b8d5..de2bbca2fe 100644
--- a/module/bug/ui/create.html.php
+++ b/module/bug/ui/create.html.php
@@ -29,6 +29,7 @@ if(!$product->shadow) $fields->fullModeOrders('module,project,execution');
jsVar('bug', $bug);
jsVar('moduleID', $bug->moduleID);
+jsVar('methodName', $app->methodName);
jsVar('tab', $this->app->tab);
jsVar('createRelease', $lang->release->create);
jsVar('refresh', $lang->refreshIcon);
diff --git a/module/bug/ui/edit.html.php b/module/bug/ui/edit.html.php
index 6f9c4511c5..6339b8b9a8 100644
--- a/module/bug/ui/edit.html.php
+++ b/module/bug/ui/edit.html.php
@@ -16,6 +16,7 @@ include($this->app->getModuleRoot() . 'ai/ui/inputinject.html.php');
jsVar('bug', $bug);
jsVar('confirmChangeProduct', $lang->bug->notice->confirmChangeProduct);
jsVar('moduleID', $bug->module);
+jsVar('methodName', $app->methodName);
jsVar('tab', $this->app->tab);
jsVar('released', $lang->build->released);
jsVar('confirmUnlinkBuild', sprintf($lang->bug->notice->confirmUnlinkBuild, zget($resolvedBuildPairs, $bug->resolvedBuild)));
diff --git a/module/bug/ui/resolve.html.php b/module/bug/ui/resolve.html.php
index a0f19371d2..2e66925df1 100644
--- a/module/bug/ui/resolve.html.php
+++ b/module/bug/ui/resolve.html.php
@@ -78,7 +78,7 @@ formPanel
set::width('1/3'),
setID('newBuildExecutionBox'),
setClass('hidden'),
- set::label(!empty($execution) && $execution->type == 'kanban' ? $lang->bug->kanban : $lang->build->execution),
+ set::label(!empty($execution) && $execution->type == 'kanban' ? $lang->bug->kanban : $lang->build->executionAB),
set::required(true),
picker
(
diff --git a/module/common/lang/menu.php b/module/common/lang/menu.php
index 521b2c364a..c4634cca04 100644
--- a/module/common/lang/menu.php
+++ b/module/common/lang/menu.php
@@ -582,7 +582,7 @@ $lang->bi->dividerMenu = ',metric,';
$lang->bi->menuOrder[5] = 'screen';
$lang->bi->menuOrder[10] = 'pivot';
$lang->bi->menuOrder[15] = 'chart';
-$lang->bi->menuOrder[50] = 'metric';
+$lang->bi->menuOrder[20] = 'metric';
/* Company menu.*/
$lang->company->menu = new stdclass();
diff --git a/module/dataview/lang/de.php b/module/dataview/lang/de.php
index 71a7ae9b9b..a43881f1df 100644
--- a/module/dataview/lang/de.php
+++ b/module/dataview/lang/de.php
@@ -35,6 +35,7 @@ $lang->dataview->add = 'Add ';
$lang->dataview->sqlQuery = 'SQL Query';
$lang->dataview->onlyOne = 'Only allow one query';
$lang->dataview->empty = 'Please enter a query statement';
+$lang->dataview->emptyBuilder = 'Please configure the builder correctly';
$lang->dataview->allowSelect = 'Only SELECT is allowed';
$lang->dataview->noStar = "For performance, 'SELECT *' is not allowed";
$lang->dataview->fieldSettings = "Field Settings";
@@ -74,10 +75,11 @@ $lang->dataview->varFilter->noticeVarName = 'Filter name cannot be empty';
$lang->dataview->varFilter->noticeRequestType = 'Request type cannot be empty';
$lang->dataview->varFilter->noticeShowName = 'Show name cannot be empty';
-$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
-$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
-$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
-$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
+$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
+$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
+$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['multipleselect'] = 'Multiple Select';
$lang->dataview->varFilter->selectList['product'] = $lang->productCommon . 'List';
$lang->dataview->varFilter->selectList['product.status'] = $lang->productCommon . 'Status';
diff --git a/module/dataview/lang/en.php b/module/dataview/lang/en.php
index 71a7ae9b9b..a43881f1df 100644
--- a/module/dataview/lang/en.php
+++ b/module/dataview/lang/en.php
@@ -35,6 +35,7 @@ $lang->dataview->add = 'Add ';
$lang->dataview->sqlQuery = 'SQL Query';
$lang->dataview->onlyOne = 'Only allow one query';
$lang->dataview->empty = 'Please enter a query statement';
+$lang->dataview->emptyBuilder = 'Please configure the builder correctly';
$lang->dataview->allowSelect = 'Only SELECT is allowed';
$lang->dataview->noStar = "For performance, 'SELECT *' is not allowed";
$lang->dataview->fieldSettings = "Field Settings";
@@ -74,10 +75,11 @@ $lang->dataview->varFilter->noticeVarName = 'Filter name cannot be empty';
$lang->dataview->varFilter->noticeRequestType = 'Request type cannot be empty';
$lang->dataview->varFilter->noticeShowName = 'Show name cannot be empty';
-$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
-$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
-$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
-$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
+$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
+$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
+$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['multipleselect'] = 'Multiple Select';
$lang->dataview->varFilter->selectList['product'] = $lang->productCommon . 'List';
$lang->dataview->varFilter->selectList['product.status'] = $lang->productCommon . 'Status';
diff --git a/module/dataview/lang/fr.php b/module/dataview/lang/fr.php
index 71a7ae9b9b..a43881f1df 100644
--- a/module/dataview/lang/fr.php
+++ b/module/dataview/lang/fr.php
@@ -35,6 +35,7 @@ $lang->dataview->add = 'Add ';
$lang->dataview->sqlQuery = 'SQL Query';
$lang->dataview->onlyOne = 'Only allow one query';
$lang->dataview->empty = 'Please enter a query statement';
+$lang->dataview->emptyBuilder = 'Please configure the builder correctly';
$lang->dataview->allowSelect = 'Only SELECT is allowed';
$lang->dataview->noStar = "For performance, 'SELECT *' is not allowed";
$lang->dataview->fieldSettings = "Field Settings";
@@ -74,10 +75,11 @@ $lang->dataview->varFilter->noticeVarName = 'Filter name cannot be empty';
$lang->dataview->varFilter->noticeRequestType = 'Request type cannot be empty';
$lang->dataview->varFilter->noticeShowName = 'Show name cannot be empty';
-$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
-$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
-$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
-$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['input'] = 'Input';
+$lang->dataview->varFilter->requestTypeList['date'] = 'Date';
+$lang->dataview->varFilter->requestTypeList['datetime'] = 'Datetime';
+$lang->dataview->varFilter->requestTypeList['select'] = 'Select';
+$lang->dataview->varFilter->requestTypeList['multipleselect'] = 'Multiple Select';
$lang->dataview->varFilter->selectList['product'] = $lang->productCommon . 'List';
$lang->dataview->varFilter->selectList['product.status'] = $lang->productCommon . 'Status';
diff --git a/module/dataview/lang/zh-cn.php b/module/dataview/lang/zh-cn.php
index 719f9dcd6a..bf42182687 100644
--- a/module/dataview/lang/zh-cn.php
+++ b/module/dataview/lang/zh-cn.php
@@ -35,6 +35,7 @@ $lang->dataview->add = '添加';
$lang->dataview->sqlQuery = 'SQL语句查询';
$lang->dataview->onlyOne = '只能输入一条SQL语句';
$lang->dataview->empty = '请输入一条正确的SQL语句';
+$lang->dataview->emptyBuilder = '请正确配置构建器';
$lang->dataview->allowSelect = '只允许SELECT查询';
$lang->dataview->noStar = "考虑性能,不允许使用 'SELECT *' 查询";
$lang->dataview->fieldSettings = "设置字段标签";
@@ -74,10 +75,11 @@ $lang->dataview->varFilter->noticeVarName = '名称不能为空';
$lang->dataview->varFilter->noticeRequestType = '筛选器类型不能为空';
$lang->dataview->varFilter->noticeShowName = '显示名称不能为空';
-$lang->dataview->varFilter->requestTypeList['input'] = '文本框';
-$lang->dataview->varFilter->requestTypeList['date'] = '日期选择';
-$lang->dataview->varFilter->requestTypeList['datetime'] = '时间选择';
-$lang->dataview->varFilter->requestTypeList['select'] = '下拉选择';
+$lang->dataview->varFilter->requestTypeList['input'] = '文本框';
+$lang->dataview->varFilter->requestTypeList['date'] = '日期选择';
+$lang->dataview->varFilter->requestTypeList['datetime'] = '时间选择';
+$lang->dataview->varFilter->requestTypeList['select'] = '下拉选择';
+$lang->dataview->varFilter->requestTypeList['multipleselect'] = '多选下拉';
$lang->dataview->varFilter->selectList['product'] = $lang->productCommon . '列表';
$lang->dataview->varFilter->selectList['product.status'] = '产品状态';
diff --git a/module/design/model.php b/module/design/model.php
index 7848a54ff3..bc905a6098 100755
--- a/module/design/model.php
+++ b/module/design/model.php
@@ -430,8 +430,8 @@ class designModel extends model
{
return $this->dao->select('t1.revision,t3.id AS id,t3.name AS title')
->from(TABLE_REPOHISTORY)->alias('t1')
- ->leftJoin(TABLE_RELATION)->alias('t2')->on('t2.relation="completedin" AND t2.BType="commit" AND t2.BID=t1.id')
- ->leftJoin(TABLE_DESIGN)->alias('t3')->on('t2.AType="design" AND t2.AID=t3.id')
+ ->leftJoin(TABLE_RELATION)->alias('t2')->on("t2.relation='completedin' AND t2.BType='commit' AND t2.BID=t1.id")
+ ->leftJoin(TABLE_DESIGN)->alias('t3')->on("t2.AType='design' AND t2.AID=t3.id")
->where('t1.revision')->in($revisions)
->andWhere('t1.repo')->eq($repoID)
->andWhere('t3.id')->ne('')
diff --git a/module/design/test/lib/assigndesign.ui.class.php b/module/design/test/lib/assigndesign.ui.class.php
new file mode 100644
index 0000000000..7c87610b1c
--- /dev/null
+++ b/module/design/test/lib/assigndesign.ui.class.php
@@ -0,0 +1,28 @@
+initForm('design', 'browse', array('projectID' => 60), 'appIframe-project');
+ $form->dom->btn($this->lang->design->noAssigned)->click();
+ if(isset($design['assignedTo'])) $form->dom->assignedTo->picker($design['assignedTo']);
+
+ $form->wait(2);
+ $form->dom->assignedToBtn->click();
+ $form->wait(1);
+
+ /* 跳转到设计列表,检查指派给字段信息。 */
+ $browsePage = $this->loadPage('design', 'browse');
+ if($browsePage->dom->assigned->getText() != $design['assignedTo']) return $this->failed('指派给错误');
+ return $this->success();
+ }
+}
diff --git a/module/design/test/lib/batchcreatedesign.ui.class.php b/module/design/test/lib/batchcreatedesign.ui.class.php
new file mode 100644
index 0000000000..7384672983
--- /dev/null
+++ b/module/design/test/lib/batchcreatedesign.ui.class.php
@@ -0,0 +1,30 @@
+initForm('design', 'batchCreate', array('projecID' => 60, 'productID' => 0), 'appIframe-project');
+ if(isset($design['type'])) $form->dom->type->picker($design['type']);
+ if(isset($design['name'])) $form->dom->name_0->setValue($design['name']);
+
+ $form->wait(1);
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(1);
+
+ /* 跳转到设计列表,检查设计字段信息。*/
+ $browsePage = $this->loadPage('design', 'browse');
+ if($browsePage->dom->designName->getText() != $design['name']) return $this->failed('设计名称错误');
+ if($browsePage->dom->designType->getText() != $design['type']) return $this->failed('设计类型错误');
+
+ return $this->success();
+ }
+}
diff --git a/module/design/test/ui/assigndesign.php b/module/design/test/ui/assigndesign.php
new file mode 100755
index 0000000000..47a11e1e6e
--- /dev/null
+++ b/module/design/test/ui/assigndesign.php
@@ -0,0 +1,27 @@
+#!/usr/bin/env php
+loadYaml('project', false, 2)->gen(10);
+zendata('design')->loadYaml('design', false, 2)->gen(2);
+$tester = new assignDesignTester();
+$tester->login();
+
+$design = array(
+ array('assignedTo' => 'admin'),
+);
+
+r($tester->assignDesign($design['0'])) && p('status') && e('SUCCESS'); //指派设计
+
+$tester->closeBrowser();
diff --git a/module/design/test/ui/batchcreatedesign.php b/module/design/test/ui/batchcreatedesign.php
new file mode 100755
index 0000000000..8f9c11bd44
--- /dev/null
+++ b/module/design/test/ui/batchcreatedesign.php
@@ -0,0 +1,30 @@
+#!/usr/bin/env php
+loadYaml('project', false, 2)->gen(10);
+zendata('design')->loadYaml('design', false, 2)->gen(0);
+$tester = new batchCreateDesignTester();
+$tester->login();
+
+$design = array(
+ array('type' => '概要设计', 'name' => '概要设计01'),
+ array('type' => '详细设计', 'name' => '详细设计01'),
+);
+
+r($tester->batchCreateDesign($design['0'])) && p('status') && e('SUCCESS'); //批量创建概要设计类型的设计
+r($tester->batchCreateDesign($design['1'])) && p('status') && e('SUCCESS'); //批量创建详细设计类型的设计
+
+$tester->closeBrowser();
diff --git a/module/design/test/ui/editdesign.php b/module/design/test/ui/editdesign.php
index 86c1e2b09d..cf8f33bfa0 100755
--- a/module/design/test/ui/editdesign.php
+++ b/module/design/test/ui/editdesign.php
@@ -19,6 +19,7 @@ cid=2
chdir(__DIR__);
include '../lib/editdesign.ui.class.php';
+zendata('project')->loadYaml('project', false, 2)->gen(10);
zendata('design')->loadYaml('design', false, 2)->gen(2);
zendata('designspec')->loadYaml('designspec', false, 2)->gen(2);
$tester = new editDesignTester();
diff --git a/module/design/test/ui/page/batchcreate.php b/module/design/test/ui/page/batchcreate.php
new file mode 100644
index 0000000000..3e7c70340d
--- /dev/null
+++ b/module/design/test/ui/page/batchcreate.php
@@ -0,0 +1,12 @@
+ "//*[@id='type_0']/div/input",
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/design/test/ui/page/browse.php b/module/design/test/ui/page/browse.php
index 415213b546..bfb14223bf 100644
--- a/module/design/test/ui/page/browse.php
+++ b/module/design/test/ui/page/browse.php
@@ -7,8 +7,17 @@ class browsePage extends page
$xpath = array(
'designName' => "//*[@id='table-design-browse']/div[2]/div[1]/div/div[2]/div/a",
- 'linkedProduct' => "//*[@id='table-design-browse']/div[2]/div[2]/div/div[1]/div",
+ 'linkedProduct' => "//*[@id='mainContent']/div[2]/div[2]/div/div[2]/table/tbody/tr[2]/td",
'designType' => "//*[@id='table-design-browse']/div[2]/div[2]/div/div[2]/div/span",
+ 'assignedTo' => "//*[@name='assignedTo']",
+ 'assignedToBtn' => "//*[@class='form load-indicator form-ajax no-morph form-horz']/div[3]/div/button/span",
+ 'assigned' => "//*[@id='table-design-browse']/div[2]/div[2]/div/div[3]/div/a/span",
+ 'allMenu' => "//*[@id='mainNavbar']/div/menu/li[1]/a/span",
+ 'hldsMenu' => "//*[@id='mainNavbar']/div/menu/li[2]/a/span",
+ 'ddsMenu' => "//*[@id='mainNavbar']/div/menu/li[3]/a/span",
+ 'dbdsMenu' => "//*[@id='mainNavbar']/div/menu/li[4]/a/span",
+ 'adsMenu' => "//*[@id='mainNavbar']/div/menu/li[5]/a/span",
+ 'designNum' => "//*[@id='table-design-browse']/div[3]/nav/div[1]",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/design/zen.php b/module/design/zen.php
index ef6ad407ab..0fbe769c38 100644
--- a/module/design/zen.php
+++ b/module/design/zen.php
@@ -32,7 +32,7 @@ class designZen extends control
/* Show custom design types. */
$this->lang->waterfall->menu->design['subMenu'] = new stdclass();
- $this->lang->waterfall->menu->design['subMenu']->all = array('link' => "{$this->lang->all}|design|browse|projectID=%s&productID={$productID}&browseType=all", 'exclude' => $type == 'all' ? '' : 'design');
+ $this->lang->waterfall->menu->design['subMenu']->all = array('link' => "{$this->lang->all}|design|browse|projectID=%s&productID={$productID}&browseType=all", 'exclude' => $type == 'all' ? '' : 'design', 'alias' => $type == 'all' ? $this->app->rawMethod : '');
$count = 1;
foreach(array_filter($this->lang->design->{$typeList}) as $key => $value)
{
diff --git a/module/doc/control.php b/module/doc/control.php
index 75f13cc53c..9654e0c9a2 100755
--- a/module/doc/control.php
+++ b/module/doc/control.php
@@ -1004,10 +1004,13 @@ class doc extends control
{
list($myObjects, $normalObjects, $closedObjects) = $this->doc->getOrderedObjects($objectType, 'nomerge', $objectID);
+ $libData = $this->doc->setMenuByType($objectType, $objectID, 0);
+
$this->view->objectType = $objectType;
$this->view->objectID = $objectID;
+ $this->view->libID = !empty($libData[1]) ? $libData[1] : 0;
$this->view->module = $module;
- $this->view->method = $method =='view' ? $objectType.'space' : $method;
+ $this->view->method = $method == 'view' ? $objectType.'space' : $method;
$this->view->normalObjects = $myObjects + $normalObjects;
$this->view->closedObjects = $closedObjects;
$this->view->objectsPinYin = common::convert2Pinyin($myObjects + $normalObjects + $closedObjects);
diff --git a/module/doc/test/lib/createdoc.ui.class.php b/module/doc/test/lib/createdoc.ui.class.php
index d7cdf9155b..46b1b85848 100644
--- a/module/doc/test/lib/createdoc.ui.class.php
+++ b/module/doc/test/lib/createdoc.ui.class.php
@@ -45,12 +45,91 @@ class createDocTester extends tester
$form->wait(1);
$form->dom->releaseBtn->click();
- $this->openUrl('doc', 'mySpace', array('objectType' => 'mine'));
- $form = $this->loadPage('doc', 'mySpace', array('objectType' => 'mine'));
+ $this->openUrl('doc', 'mySpace', array('objectType' => 'createdby'));
+ $form = $this->loadPage('doc', 'mySpace', array('objectType' => 'createdby'));
$form->dom->search(array("文档标题,=,{$docName->dcName}"));
$form->wait(1);
if($form->dom->fstDocName->getText() != $docName->dcName) return $this->failed('文档创建失败');
return $this->success('文档创建成功');
}
+
+ /*
+ * 创建产品文档。
+ * Create a product doc.
+ *
+ * @param string $productName
+ * @param string $docName
+ * @access public
+ * @return void
+ */
+ public function createProductDoc($productName, $docName)
+ {
+ /*创建两个产品*/
+ $form = $this->initForm('product', 'create');
+ $form->dom->name->setValue($productName->fstProduct);
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(1);
+ $form = $this->initForm('product', 'create');
+ $form->dom->name->setValue($productName->secProduct);
+ $form->dom->btn($this->lang->save)->click();
+
+ /*创建产品下的文档*/
+ $this->openUrl('doc', 'productSpace');
+ $form = $this->loadPage('doc', 'productSpace');
+ $form->dom->createDocBtn->click();
+ $form->wait(1);
+ $form->dom->showTitle->setValue($docName->dcName);
+ $form->dom->saveBtn->click();
+ $form->wait(1);
+ $form->dom->product->picker($productName->secProduct);
+ $form->dom->releaseBtn->click();
+
+ if($form->dom->leftListHeader->getText() != $productName->secProduct) return $this->failed('切换产品创建文档失败');
+ return $this->success('切换产品创建文档成功');
+ }
+
+ /*
+ * 创建项目文档。
+ * Create a project doc.
+ *
+ * @param string $projectName
+ * @param string $executionName
+ * @param string $plan
+ * @param string $docName
+ * @access public
+ * @return void
+ */
+ public function createProjectDoc($projectName, $executionName, $plan, $docName)
+ {
+ /*创建项目*/
+ $form = $this->initForm('project', 'create', array('modal' => 'scrum'));
+ $form->dom->hasProduct0->click();
+ $form->dom->name->setValue($projectName->fstProject);
+ $form->dom->begin->datePicker($plan->begin);
+ $form->dom->longTime->click();
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(2);
+
+ /*创建项目下的执行*/
+ $form = $this->initForm('execution', 'create');
+ $form->dom->project->picker($projectName->fstProject);
+ $form->dom->name->setValue($executionName->fstExecution);
+ $form->dom->begin->datePicker($plan->begin);
+ $form->dom->end->datePicker($plan->end);
+ $form->dom->btn($this->lang->save)->click();
+
+ /*创建项目空间下的文档*/
+ $this->openUrl('doc', 'projectSpace');
+ $form = $this->loadPage('doc', 'projectSpace');
+ $form->dom->createDocBtn->click();
+ $form->wait(1);
+ $form->dom->showTitle->setValue($docName->dcName);
+ $form->dom->saveBtn->click();
+ $form->wait(1);
+ $form->dom->project->picker($projectName->fstProject);
+ $form->dom->execution->picker($executionName->fstExecution);
+ $form->wait(1);
+ $form->dom->releaseBtn->click();
+ }
}
diff --git a/module/doc/test/lib/editdoc.ui.class.php b/module/doc/test/lib/editdoc.ui.class.php
index 66a7823de1..87bd28e865 100644
--- a/module/doc/test/lib/editdoc.ui.class.php
+++ b/module/doc/test/lib/editdoc.ui.class.php
@@ -7,6 +7,7 @@ class createDocTester extends tester
* Edit a doc.
*
* @param string $editDocName
+ * @param string $docName
* @access public
* @return void
*/
@@ -31,8 +32,8 @@ class createDocTester extends tester
$form->dom->saveDraftBtn->click();
$form->wait(1);
- $this->openUrl('doc', 'mySpace', array('objectType' => 'mine'));
- $form = $this->loadPage('doc', 'mySpace', array('objectType' => 'mine'));
+ $this->openUrl('doc', 'mySpace', array('objectType' => 'editedby'));
+ $form = $this->loadPage('doc', 'mySpace', array('objectType' => 'editedby'));
$form->dom->search(array("文档标题,=,{$editDocName->editName}"));
$form->wait(1);
@@ -44,7 +45,7 @@ class createDocTester extends tester
* 移动文档。
* Move a doc.
*
- * @param string $editDocName
+ * @param string $libName
* @access public
* @return void
*/
@@ -69,14 +70,13 @@ class createDocTester extends tester
$form->wait(1);
if($form->dom->leftListHeader->getText() != $llibName->myDocLib) return $this->failed('文档移动失败');
- return $this->success('文档移动失败');
+ return $this->success('文档移动成功');
}
/**
* 删除文档
* Delete a doc.
*
- * @param string $editDocName
* @access public
* @return void
*/
diff --git a/module/doc/test/lib/editdoclib.ui.class.php b/module/doc/test/lib/editdoclib.ui.class.php
index 494a103611..ec84459225 100644
--- a/module/doc/test/lib/editdoclib.ui.class.php
+++ b/module/doc/test/lib/editdoclib.ui.class.php
@@ -6,7 +6,8 @@ class createDocTester extends tester
* 编辑我的文档库。
* Edit a doclib.
*
- * @param string $docLibName
+ * @param string $libName
+ * @param string $editLibName
* @access public
* @return void
*/
@@ -37,7 +38,7 @@ class createDocTester extends tester
* 删除一个文档库。
* Delete a docLib.
*
- * @param string $docLibName
+ * @param string $editLibName
* @access public
* @return void
*/
diff --git a/module/doc/test/lib/lefttree.ui.class.php b/module/doc/test/lib/lefttree.ui.class.php
new file mode 100644
index 0000000000..dd44f49d24
--- /dev/null
+++ b/module/doc/test/lib/lefttree.ui.class.php
@@ -0,0 +1,35 @@
+openUrl('doc', 'mySpace', array('type' => 'mine'));
+ $form = $this->loadPage('doc', 'mySpace', array('type' => 'mine'));
+ $form->dom->createDocBtn->click();
+ $form->wait(1);
+ $form->dom->showTitle->setValue($docName->dcName);
+ $form->dom->saveBtn->click();
+ $form->wait(1);
+ $form->dom->releaseBtn->click();
+
+ /*收藏文档*/
+ $this->openUrl('doc', 'mySpace', array('type' => 'mine'));
+ $form = $this->loadPage('doc', 'mySpace', array('type' => 'mine'));
+ $form->dom->fstCollectBtn->click();
+ $form->wait(1);
+ $form->dom->myFavorites->click();
+
+ if($form->dom->checkFstDoc->getText() != $docName->dcName) return $this->failed('收藏文档失败');
+ return $this->success('收藏文档成功');
+ }
+}
diff --git a/module/doc/test/ui/createdoc.php b/module/doc/test/ui/createdoc.php
index f19b180d98..f3ac584a30 100644
--- a/module/doc/test/ui/createdoc.php
+++ b/module/doc/test/ui/createdoc.php
@@ -1,6 +1,26 @@
#!/usr/bin/env php
login();
$draftName = new stdClass();
$draftName->nullName = '';
-$draftName->dftName = '我的草稿文档1';
+$draftName->dftName = '草稿文档1';
$docName = new stdClass();
-$docName->dcName = '我的文档1';
+$docName->dcName = '文档1';
-r($tester->createDraft($draftName)) && p('message,status') && e('创建草稿表单页提示信息正确,SUCCESS');
-r($tester->createDoc($docName)) && p('message,status') && e('创建文档表单页提示信息正确,SUCCESS');
+$productName = new stdClass();
+$productName->fstProduct = '产品1';
+$productName->secProduct = '产品2';
+
+$projectName = new stdClass();
+$projectName->fstProject = '项目1';
+
+$executionName = new stdClass();
+$executionName->fstExecution = '执行1';
+
+$plan = new stdClass();
+$plan->begin = '2024-09-01';
+$plan->end = '2024-11-01';
+
+r($tester->createDraft($draftName)) && p('message,status') && e('创建草稿成功,SUCCESS'); //创建草稿文档成功
+r($tester->createDoc($docName)) && p('message,status') && e('创建文档成功,SUCCESS'); //创建文档成功
+r($tester->createProductDoc($productName, $docName)) && p('message,status') && e('创建产品文档成功,SUCCESS'); //创建产品空间下的文档成功
+r($tester->createProjectDoc($projectName, $executionName, $plan, $docName)) && p('message,status') && e('创建项目文档成功,SUCCESS'); //创建项目空间下的文档成功
diff --git a/module/doc/test/ui/lefttree.php b/module/doc/test/ui/lefttree.php
new file mode 100755
index 0000000000..bfdc4f9028
--- /dev/null
+++ b/module/doc/test/ui/lefttree.php
@@ -0,0 +1,24 @@
+#!/usr/bin/env php
+login();
+
+$docName = new stdClass();
+$docName->dcName = '我的文档A';
+
+r($tester->myFavorites($docName)) && p('message,status') && e('收藏文档成功,SUCCESS'); //收藏文档成功
\ No newline at end of file
diff --git a/module/doc/test/ui/page/myspace.php b/module/doc/test/ui/page/myspace.php
index 990e739c60..21a83e620a 100644
--- a/module/doc/test/ui/page/myspace.php
+++ b/module/doc/test/ui/page/myspace.php
@@ -8,9 +8,9 @@ class myspacePage extends page
'createLibBtn' => '/html/body/div[1]/div/div[1]/div[2]/a',
'leftListHeader' => '/html/body/div[1]/div/div[2]/div[1]/header/span',
'libName' => '//*[@id="zin_doc_createlib_form"]/div[1]/div[1]/input',
- 'fstDocLib' => '/html/body/div[1]/div/div[2]/div[2]/div[2]/div/div[2]/div[1]/div/div[2]/div/div/div/a[1]',
'createDocBtn' => '/html/body/div/div/div[1]/div[2]/div',
- 'fstDocName' => '/html/body/div/div/div[2]/div[2]/div/div/div[2]/div[1]/div/div[2]/div/div/div/a[1]',
+ 'fstDocName' => '/html/body/div[1]/div/div[2]/div[2]/div[2]/div/div[2]/div[1]/div/div[2]/div/a',
+ 'fstDocLabel' => '/html/body/div[1]/div/div[2]/div[2]/div[2]/div/div[2]/div[1]/div/div[2]/div/div[2]/span',
'saveDraftBtn' => '/html/body/div[1]/div/div/div[2]/form/div[1]/div[1]/div/div/button',
'alertTitle' => '//*[@class="modal modal-async load-indicator modal-alert modal-trans show in"]/div[1]/div[1]/div[2]/div[1]',
'saveBtn' => '/html/body/div[1]/div/div/div[2]/form/div[1]/div[1]/div/div/a',
@@ -19,12 +19,17 @@ class myspacePage extends page
'fstMoreBtn' => '//*[@class="tree-item item is-nested is-nested-show"]/menu[1]/li[2]/div[1]/nav[1]/button[1]',
'fstDocLib' => '/html/body/div[1]/div/div[2]/div[1]/div[1]/div/main/menu/li[1]/menu/li[2]/div/div/a',
'editLib' => '//*[@class="popover show fade dropdown in"]/menu[1]/menu[1]/li[3]/a[1]',
- 'fstDocLib' => '/html/body/div[1]/div/div[2]/div[1]/div[1]/div/main/menu/li[1]/menu/li[2]/div/div/a',
'deleteAccept' => '/html/body/div[3]/div/div/div[3]/nav/button[1]',
'fstMoveBtn' => '/html/body/div[1]/div/div[2]/div[2]/div/div/div[2]/div[3]/div/div/div/nav/a[2]/i',
'fstDeleteBtn' => '/html/body/div[1]/div/div[2]/div[2]/div/div/div[2]/div[3]/div/div/div/nav/a[3]/i',
'formText' => '/html/body/div/div/div[2]/div[2]/div/div/div/div/div',
'saveMoveBtn' => '//*[@class="m-doc-myspace"]/div[2]/div[1]/div[1]/div[3]/div[1]/div[1]/form[1]/div[6]/div[1]/button[1]',
+ 'checkFstDoc' => '/html/body/div[1]/div/div[2]/div[2]/div/div/div[2]/div[1]/div/div[2]/div/a',
+ 'fstCollectBtn' => '/html/body/div[1]/div/div[2]/div[2]/div/div/div[2]/div[1]/div/div[2]/div/div[2]/a/img',
+ 'myFavorites' => '/html/body/div[1]/div/div[2]/div[1]/div[1]/div/main/menu/li[3]/div/div/a',
+ 'createdBy' => '/html/body/div[1]/div/div[2]/div[1]/div[1]/div/main/menu/li[4]/div/div/a',
+ 'myLibMoreBtn' => '/html/body/div[1]/div/div[2]/div[1]/div[1]/div/main/menu/li[1]/menu/li[1]/div/nav/button/i',
+ 'addDir' => '/html/body/div[2]/menu/menu/li[1]/a/div/div',
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/doc/test/ui/page/productspace.php b/module/doc/test/ui/page/productspace.php
new file mode 100644
index 0000000000..dc5eac6f70
--- /dev/null
+++ b/module/doc/test/ui/page/productspace.php
@@ -0,0 +1,15 @@
+ '/html/body/div[1]/div/div[1]/div[2]/div/a',
+ 'saveBtn' => '/html/body/div[1]/div/div/div[2]/form/div[1]/div[1]/div/div/a',
+ 'releaseBtn' => '/html/body/div[1]/div/div/div[2]/form/div[2]/div/div/div[3]/div[10]/div/button',
+ 'leftListHeader' => '/html/body/div[1]/div/div/div[1]/div[1]/div[1]/button/span',
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/doc/test/ui/page/projectspace.php b/module/doc/test/ui/page/projectspace.php
new file mode 100644
index 0000000000..782a4e736d
--- /dev/null
+++ b/module/doc/test/ui/page/projectspace.php
@@ -0,0 +1,14 @@
+ '/html/body/div[1]/div/div[1]/div[2]/div/a',
+ 'saveBtn' => '/html/body/div[1]/div/div/div[2]/form/div[1]/div[1]/div/div/a',
+ 'releaseBtn' => '/html/body/div[1]/div/div/div[2]/form/div[2]/div/div/div[3]/div[10]/div/button',
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/doc/ui/ajaxgetdropmenu.html.php b/module/doc/ui/ajaxgetdropmenu.html.php
index a2db88f783..1d6effac2e 100644
--- a/module/doc/ui/ajaxgetdropmenu.html.php
+++ b/module/doc/ui/ajaxgetdropmenu.html.php
@@ -53,8 +53,10 @@ $tabs[] = array('name' => 'closed', 'text' => $lang->doc->closed);
* 定义最终的 JSON 数据。
* Define the final json data.
*/
-$params = $method == 'showfiles' ||$objectType == 'custom' ? "type=$objectType&objectID=%s" : "objectID=%s";
-$link = $this->createLink($module, $method, $params);
+$params = "objectID=%s";
+if($method == 'showfiles' || $objectType == 'custom') $params = "type=$objectType&objectID=%s";
+if($method == 'create') $params = "objectType=$objectType&objectID=%s&libID=$libID&moduleID=0";
+$link = $this->createLink($module, $method, $params);
$json = array();
$json['data'] = $data;
diff --git a/module/execution/test/lib/bug.ui.class.php b/module/execution/test/lib/bug.ui.class.php
new file mode 100644
index 0000000000..d407e328d8
--- /dev/null
+++ b/module/execution/test/lib/bug.ui.class.php
@@ -0,0 +1,82 @@
+initForm('execution', 'bug', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->$tab->click();
+ $form->wait(1);
+ if($form->dom->num->getText() == $expectNum) return $this->success($tab . '下显示条数正确');
+ return $this->failed($tab . '下显示条数不正确');
+ }
+
+ /**
+ * 单个指派bug。
+ * Assign bug.
+ *
+ * @param string $user
+ * @access public
+ * @return object
+ */
+ public function assignTo($user)
+ {
+ $form = $this->initForm('execution', 'bug', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->firstAssignedTo->click();
+ $form->dom->assignedTo->picker($user);
+ $form->dom->submitBtn->click();
+ $form->wait(1);
+
+ if($form->dom->firstAssignedTo->getText() == $user) return $this->success('指派bug成功');
+ return $this->failed('指派bug失败');
+ }
+
+ /**
+ * 批量指派bug。
+ * Batch assign bug.
+ *
+ * @access public
+ * @return object
+ */
+ public function batchAssignTo()
+ {
+ $form = $this->initForm('execution', 'bug', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->firstCheckbox->click();
+ $form->dom->batchAssignBtn->click();
+ $form->wait(1);
+ $form->dom->assignToAdmin->click();
+ $form->wait(1);
+
+ if($form->dom->firstAssignedTo->getText() == 'admin') return $this->success('批量指派bug成功');
+ return $this->failed('批量指派bug失败');
+ }
+
+ /**
+ * 切换产品查看buig。
+ * Switch product to view bug.
+ *
+ * @param string $product firstProduct|secondProduct|thirdProduct
+ * @param string $expectNum
+ * @access public
+ * @return object
+ */
+ public function switchProduct($product, $expectNum)
+ {
+ $form = $this->initForm('execution', 'bug', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->productNav->click();
+ $form->dom->$product->click();
+ $form->wait(1);
+
+ if($form->dom->num->getText() == $expectNum) return $this->success('切换产品查看bug成功');
+ return $this->failed('切换产品查看bug失败');
+ }
+}
diff --git a/module/execution/test/lib/importbug.ui.class.php b/module/execution/test/lib/importbug.ui.class.php
new file mode 100644
index 0000000000..0648fce922
--- /dev/null
+++ b/module/execution/test/lib/importbug.ui.class.php
@@ -0,0 +1,38 @@
+initForm('execution', 'task', array('execution' => $executionId), 'appIframe-execution');
+ $form->dom->btn($this->lang->import)->click();
+ $form->dom->btn($this->lang->execution->importBug)->click();
+
+ $importForm = $this->loadPage('execution', 'importBug');
+ $importForm->wait(1);
+ if($importForm->dom->num === false)
+ {
+ if ($expectNum == '0') return $this->success('可导入的Bug数目正确');
+ return $this->failed('可导入的Bug数目不正确');
+ }
+ if($importForm->dom->num->getText() != $expectNum) return $this->failed('可导入的Bug数目不正确');
+ $id = $importForm->dom->firstId->getText();
+ $importForm->dom->firstCheckbox->click();
+ $importForm->dom->saveBtn->click();
+ $importForm->wait(1);
+ $importForm->dom->btn($this->lang->goback)->click();
+
+ $form->dom->search(array("{$this->lang->task->fromBugID},=,{$id}"));
+ if($form->dom->firstName === false) return $this->failed('导入Bug失败');
+ return $this->success('导入Bug成功');
+ }
+}
diff --git a/module/execution/test/lib/importtask.ui.class.php b/module/execution/test/lib/importtask.ui.class.php
new file mode 100644
index 0000000000..2bb3d6dde7
--- /dev/null
+++ b/module/execution/test/lib/importtask.ui.class.php
@@ -0,0 +1,46 @@
+initForm('execution', 'task', array('execution' => '3'), 'appIframe-execution');
+ $form->dom->btn($this->lang->import)->click();
+ $form->dom->btn($this->lang->execution->importTask)->click();
+
+ $importForm = $this->loadPage('execution', 'importTask');
+ $importForm->wait(1);
+
+ $executionList = $importForm->dom->getPickerItems('execution');
+ $executions = array_column($executionList, 'text');
+ if(!in_array($execution, $executions))
+ {
+ if($exist == '0') return $this->success('执行下拉列表执行显示正确');
+ return $this->falled('执行下拉列表执行显示错误');
+ }
+ if($exist == '0') return $this->failed('执行下拉列表执行显示错误');
+
+ $importForm->dom->execution->picker($execution);
+ $importForm->wait(1);
+ if($importForm->dom->num->getText() != $expectNum) return $this->failed('可导入需求不正确');
+ $name = $importForm->dom->firstName->getText();
+ $importForm->dom->firstCheckbox->click();
+ $importForm->dom->saveBtn->click();
+ $form->wait(1);
+ $importForm->dom->btn($this->lang->goback)->click();
+
+ $form->dom->search(array("{$this->lang->task->name},=,{$name}"));
+ if($form->dom->firstName === false) return $this->failed('导入任务失败');
+ return $this->success('导入任务成功');
+ }
+}
diff --git a/module/execution/test/lib/story.ui.class.php b/module/execution/test/lib/story.ui.class.php
new file mode 100755
index 0000000000..2e85c2d10e
--- /dev/null
+++ b/module/execution/test/lib/story.ui.class.php
@@ -0,0 +1,149 @@
+initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->$tab->click();
+ $form->wait(1);
+ if($form->dom->num->getText() == $expectNum) return $this->success($tab . '下显示条数正确');
+ return $this->failed($tab . '下显示条数不正确');
+ }
+
+ /**
+ * 移除单个需求。
+ * Unlink story.
+ *
+ * @access public
+ * @return object
+ */
+ public function unlinkStory()
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $name = $form->dom->firstName->getText();
+ $form->dom->firstUnlinkBtn->click();
+ $form->dom->alertModal();
+ $form->wait(1);
+
+ $form->dom->search(array("{$this->lang->story->name},=,{$name}"));
+ $form->wait(1);
+ if($form->dom->firstName === false) return $this->success('需求移除成功');
+ return $this->failed('需求移除失败');
+ }
+
+ /**
+ * 批量移除需求。
+ * Batch unlink story.
+ *
+ * @access public
+ * @return object
+ */
+ public function batchUnlinkStory()
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $name = $form->dom->firstName->getText();
+ $form->dom->firstCheckbox->click();
+ $form->dom->btn($this->lang->execution->unlinkStory)->click();
+ $form->wait(1);
+ $form->dom->alertModal();
+ $form->wait(1);
+
+ $form->dom->search(array("{$this->lang->story->name},=,{$name}"));
+ $form->wait(1);
+ if($form->dom->firstName === false) return $this->success('需求批量移除成功');
+ return $this->failed('需求批量移除失败');
+ }
+
+ /**
+ * 批量编辑阶段。
+ * Batch edit phase.
+ *
+ * @param string $status draft|reviewing|active|changing|closed
+ * @param string $phase wait|planned|projected|designing|designed|developing|developed|testing|tested|verified|rejected|delivering|delivered|released|closed
+ * @access public
+ * @return object
+ */
+ public function batchEditPhase($status, $phase)
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $storyStatus = $this->lang->story->statusList->$status;
+ $storyPhase = $this->lang->story->stageList->$phase;
+
+ $form->dom->xpath['stage'] = $form->dom->xpath['phases'] . "//*[text() = '{$storyPhase}']";
+
+ $form->dom->search(array("{$this->lang->story->status},=,{$storyStatus}"));
+ $form->wait(1);
+ $beforePhase = $form->dom->firstPhase->getText();
+ $form->dom->firstCheckbox->click();
+ $form->dom->phaseBtn->click();
+ $form->wait(1);
+ $form->dom->stage->click();
+ $form->wait(1);
+ if($status == 'draft' || $status == 'closed') $form->dom->alertModal();
+ $form->wait(1);
+
+ $afterPhase = $form->dom->firstPhase->getText();
+ if($status == 'draft' || $status == 'closed')
+ {
+ if($afterPhase == $beforePhase) return $this->success('批量编辑' . $status . '阶段成功');
+ return $this->failed('批量编辑' . $status . '阶段失败');
+ }
+ else
+ {
+ if($afterPhase == $storyPhase) return $this->success('批量编辑' . $status . '阶段成功');
+ return $this->failed('批量编辑' . $status . '阶段失败');
+ }
+ }
+
+ /**
+ * 需求指派。
+ * Assign story.
+ *
+ * @param string $user
+ * @access public
+ * @return object
+ */
+ public function assignTo($user)
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->firstAssignTo->click();
+ $form->dom->assignedTo->picker($user);
+ $form->dom->submitBtn->click();
+ $form->wait(1);
+
+ $assignedTo = $form->dom->firstAssignTo->getText();
+ if($assignedTo == $user) return $this->success('指派成功');
+ return $this->failed('指派失败');
+ }
+
+ /**
+ * 需求批量指派。
+ * Batch assign story.
+ *
+ * @access public
+ * @return object
+ */
+ public function batchAssignTo()
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+ $form->dom->firstCheckbox->click();
+ $form->dom->batchAssignBtn->click();
+ $form->wait(1);
+ $form->dom->assignToAdmin->click();
+ $form->wait(1);
+
+ $assignedTo = $form->dom->firstAssignTo->getText();
+ if($assignedTo == 'admin') return $this->success('批量指派成功');
+ return $this->failed('批量指派失败');
+ }
+}
diff --git a/module/execution/test/lib/storyestimate.ui.class.php b/module/execution/test/lib/storyestimate.ui.class.php
new file mode 100644
index 0000000000..5d9f6582c8
--- /dev/null
+++ b/module/execution/test/lib/storyestimate.ui.class.php
@@ -0,0 +1,95 @@
+initForm('execution', 'story', array('execution' => '2'), 'appIframe-execution');
+
+ $form->dom->xpath['firstEstimateBtn'] = "//a[@title = '{$this->lang->execution->storyEstimate}']";
+ $form->dom->firstEstimateBtn->click();
+ if(is_object($form->dom->reestimate)) $form->dom->reestimate->click();
+ if(isset($estimate[0])) $form->dom->estimateA->setValue($estimate[0]);
+ if(isset($estimate[1])) $form->dom->estimateB->setValue($estimate[1]);
+ if(isset($estimate[2])) $form->dom->estimateC->setValue($estimate[2]);
+ $form->wait(1);
+ $form->dom->saveBtn->click();
+ }
+
+ /**
+ * 需求估算。
+ * Story estimate.
+ *
+ * @param array $estimate
+ * @param string $time
+ * @access public
+ * @return void
+ */
+ public function storyEstimate($estimate, $time)
+ {
+ $this->inputForm($estimate);
+ $form = $this->loadPage();
+ $round = sprintf($this->lang->story->estimateRound, $time);
+ $form->dom->round->picker($round);
+ $form->wait(1);
+ $a = $form->dom->estimateA->getValue();
+ $b = $form->dom->estimateB->getValue();
+ $c = $form->dom->estimateC->getValue();
+ $ave = $form->dom->average->attr('value');
+
+ if($a != $estimate[0] || $b != $estimate[1] || $c != $estimate[2] || $ave != $estimate['averge']) return $this->failed('估算失败');
+ return $this->success('估算成功');
+ }
+
+ /**
+ * 需求估算值为非数字或负数。
+ * Story estimate value is not a number or negative.
+ *
+ * @param array $estimate
+ * @param string $type notNumber|negative
+ * @access public
+ * @return void
+ */
+ public function checkErrorInfo($estimate, $type)
+ {
+ $this->inputForm($estimate);
+ $form = $this->loadPage();
+ $form->wait(1);
+ if($type == 'notNumber')
+ {
+ if($form->dom->estimateTip->getText() == $this->lang->story->estimateMustBeNumber) return $this->success('估算值为非数字提示成功');
+ return $this->failed('估算值为非数字提示失败');
+ }
+ else
+ {
+ if($form->dom->estimateTip->getText() == $this->lang->story->estimateMustBePlus) return $this->success('估算值为负数提示成功');
+ return $this->failed('估算值为负数提示失败');
+ }
+ }
+
+ /**
+ * 执行没有团队成员时需求估算。
+ * Story estimate when no team member.
+ *
+ * @access public
+ * @return void
+ */
+ public function noTeamInfo()
+ {
+ $form = $this->initForm('execution', 'story', array('execution' => '3'), 'appIframe-execution');
+
+ $form->dom->xpath['firstEstimateBtn'] = "//a[@title = '{$this->lang->execution->storyEstimate}']";
+ $form->dom->firstEstimateBtn->click();
+ $form->wait(1);
+ if($form->dom->noTeamInfo->getText() == $this->lang->execution->noTeam) return $this->success('没有团队成员提示成功');
+ return $this->failed('没有团队成员提示失败');
+ }
+}
diff --git a/module/execution/test/ui/bug.php b/module/execution/test/ui/bug.php
new file mode 100644
index 0000000000..9411176480
--- /dev/null
+++ b/module/execution/test/ui/bug.php
@@ -0,0 +1,76 @@
+id->range('1-100');
+$product->name->range('产品1, 产品2');
+$product->type->range('normal');
+$product->gen(2);
+
+$project = zenData('project');
+$project->id->range('1-100');
+$project->project->range('0, 1, 1');
+$project->model->range('scrum, []{2}');
+$project->type->range('project, sprint{2}');
+$project->auth->range('extend, []{2}');
+$project->storytype->range('`story,epic,requirement`');
+$project->path->range('`,1,`, `,1,2,`, `,1,3,`');
+$project->grade->range('1');
+$project->name->range('项目1, 项目1执行1, 项目1执行2');
+$project->hasProduct->range('1');
+$project->status->range('wait');
+$project->acl->range('open');
+$project->gen(3);
+
+$projectProduct = zenData('projectproduct');
+$projectProduct->project->range('1-3, 1-3');
+$projectProduct->product->range('1{3}, 2{3}');
+$projectProduct->gen(6);
+
+$user = zenData('user');
+$user->id->range('1-100');
+$user->dept->range('0');
+$user->account->range('admin, user1, user2');
+$user->realname->range('admin, USER1, USER2');
+$user->password->range('77839ef72f7b71a3815a77d038e267e0');
+$user->gen(3);
+
+$team = zenData('team');
+$team->id->range('1-100');
+$team->root->range('1{3}, 2{3}');
+$team->type->range('project{3}, execution{3}');
+$team->account->range('admin, user1, user2, admin, user1, user2');
+$team->gen(6);
+
+$bug = zenData('bug');
+$bug->id->range('1-100');
+$bug->project->range('1');
+$bug->product->range('1{9}, 2{9}');
+$bug->execution->range('2');
+$bug->title->range('1-100');
+$bug->status->range('active{2}, resolved{3}, closed{5}, active{2}, resolved{3}, closed{5}');
+$bug->assignedTo->range('[]');
+$bug->gen(18);
+
+$tester = new bugTester();
+$tester->login();
+
+/* 检查标签下统计数据 */
+r($tester->checkTab('allTab', '18')) && p('message') && e('allTab下显示条数正确');
+r($tester->checkTab('unresolvedTab', '4')) && p('message') && e('unresolvedTab下显示条数正确');
+/* 指派bug */
+r($tester->assignTo('USER1')) && p('message') && e('指派bug成功');
+r($tester->batchAssignTo()) && p('message') && e('批量指派bug成功');
+/* 切换产品 */
+r($tester->switchProduct('firstProduct', '18')) && p('message') && e('切换产品查看bug成功');
+r($tester->switchProduct('secondProduct', '9')) && p('message') && e('切换产品查看bug成功');
+r($tester->switchProduct('thirdProduct', '9')) && p('message') && e('切换产品查看bug成功');
+$tester->closeBrowser();
diff --git a/module/execution/test/ui/importbug.php b/module/execution/test/ui/importbug.php
new file mode 100644
index 0000000000..55961cc0ad
--- /dev/null
+++ b/module/execution/test/ui/importbug.php
@@ -0,0 +1,57 @@
+id->range('1-100');
+$product->name->range('产品1, 产品2');
+$product->type->range('normal');
+$product->gen(2);
+
+$project = zenData('project');
+$project->id->range('1-100');
+$project->project->range('0, 1{3}');
+$project->model->range('scrum, []{3}');
+$project->type->range('project, sprint{3}');
+$project->auth->range('extend, []{3}');
+$project->storytype->range('`story,epic,requirement`');
+$project->path->range('`,1,`, `,1,2,`, `,1,3,`, `,1,4,`');
+$project->grade->range('1');
+$project->name->range('项目1, 项目1执行1, 项目1执行2, 项目1执行3');
+$project->hasProduct->range('1');
+$project->status->range('wait');
+$project->acl->range('open');
+$project->gen(5);
+
+$projectProduct = zenData('projectproduct');
+$projectProduct->project->range('1-3');
+$projectProduct->product->range('1{2}, 2{3}');
+$projectProduct->gen(5);
+
+$bug = zenData('bug');
+$bug->id->range('1-100');
+$bug->project->range('0');
+$bug->product->range('1{5}, 2{5}');
+$bug->execution->range('0');
+$bug->task->range('0');
+$bug->toTask->range('0');
+$bug->title->range('1-100');
+$bug->status->range('active{3}, resolved, closed');
+$bug->deleted->range('1, 0{4}');
+$bug->gen(10);
+
+$tester = new importBugTester();
+$tester->login();
+
+r($tester->importBug('4', '0')) && p('status,message') && e('success','可导入的Bug数目正确');
+r($tester->importBug('3', '2')) && p('status,message') && e('success','导入Bug成功');
+r($tester->importBug('2', '3')) && p('status,message') && e('success','导入Bug成功');
+r($tester->importBug('2', '2')) && p('status,message') && e('success','导入Bug成功');
+$tester->closeBrowser();
diff --git a/module/execution/test/ui/importtask.php b/module/execution/test/ui/importtask.php
new file mode 100644
index 0000000000..b7bc028540
--- /dev/null
+++ b/module/execution/test/ui/importtask.php
@@ -0,0 +1,56 @@
+id->range('1-100');
+$project->project->range('0, 1{7}, 0, 9');
+$project->model->range('scrum, []{7}, scrum, []');
+$project->type->range('project, sprint{7}, project, sprint');
+$project->auth->range('extend, []{7}, extend, []');
+$project->storytype->range('`story,epic,requirement`');
+$project->path->range('`,1,`, `,1,2,`, `,1,3,`, `,1,4,`, `,1,5,`, `,1,6,`, `,1,7,`, `,1,8,`, `,9,`, `,9,10`');
+$project->grade->range('1');
+$project->name->range('项目1, 已删除执行, 未开始执行1, 未开始执行2, 进行中执行, 已挂起执行, 已关闭执行, 无任务执行, 项目2, 项目2执行');
+$project->hasProduct->range('1');
+$project->status->range('doing, wait{3}, doing, suspended, closed, wait{3}');
+$project->acl->range('open');
+$project->deleted->range('0, 1, 0{100}');
+$project->gen(10);
+
+$task = zenData('task');
+$task->id->range('1-100');
+$task->project->range('9{7}, 1{100}');
+$task->parent->range('0');
+$task->execution->range('10{7}, 2{7}, 3{7}, 4{7}, 5{7}, 6{7}, 7{7}');
+$task->story->range('0');
+$task->designVersion->range('1');
+$task->name->range('1-100');
+$task->status->range('wait, wait, doing, done, pause, cancel, closed');
+$task->deleted->range('1, 0{6}');
+$task->gen(49);
+
+$taskSpec = zenData('taskspec');
+$taskSpec->task->range('1-100');
+$taskSpec->version->range('1');
+$taskSpec->name->range('已删除, 未开始, 进行中, 已完成, 已暂停, 已取消, 已关闭');
+$taskSpec->gen(49);
+
+$tester = new importTaskTester();
+$tester->login();
+
+r($tester->importTask('项目1 / 已删除执行','4', '0')) && p('message') && e('执行下拉列表执行显示正确');
+r($tester->importTask('项目1 / 未开始执行2','4')) && p('message') && e('导入任务成功');
+r($tester->importTask('项目1 / 进行中执行', '4')) && p('message') && e('导入任务成功');
+r($tester->importTask('项目1 / 已挂起执行', '4')) && p('message') && e('导入任务成功');
+r($tester->importTask('项目1 / 已关闭执行', '4', '0')) && p('message') && e('执行下拉列表执行显示正确');
+r($tester->importTask('项目1 / 无任务执行', '4', '0')) && p('message') && e('执行下拉列表执行显示正确');
+r($tester->importTask('项目2 / 项目2执行', '4', '0')) && p('message') && e('执行下拉列表执行显示正确');
+$tester->closeBrowser();
diff --git a/module/execution/test/ui/page/bug.php b/module/execution/test/ui/page/bug.php
new file mode 100755
index 0000000000..3a29ce4c4b
--- /dev/null
+++ b/module/execution/test/ui/page/bug.php
@@ -0,0 +1,28 @@
+ "//*[@id='featureBar']/menu/li[1]/a",
+ 'unresolvedTab' => "//*[@id='featureBar']/menu/li[2]/a",
+ 'num' => "//*[@id='table-execution-bug']/div[3]/div[2]/strong[1]",
+ /* 列表 */
+ 'firstCheckbox' => "//*[@id='table-execution-bug']/div[2]/div[1]/div/div[1]/div/div",
+ 'firstAssignedTo' => "//*[@id='table-execution-bug']/div[2]/div[2]/div/div[7]/div/a/span",
+ /* 批量操作按钮 */
+ 'batchAssignBtn' => "//*[@id='table-execution-bug']/div[3]/nav[1]/button",
+ 'assignToAdmin' => "//li//div[text() = 'admin']",
+ /* bug指派弹窗 */
+ 'submitBtn' => "//*[@id='assignedTo']/../../div[4]/div/button",
+ /*1.5级产品导航 */
+ 'productNav' => "//*[@id='pick-execution-menu']",
+ 'firstProduct' => "(//div[@data-type='product'])[1]",
+ 'secondProduct' => "(//div[@data-type='product'])[2]",
+ 'thirdProduct' => "(//div[@data-type='product'])[3]",
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/execution/test/ui/page/importbug.php b/module/execution/test/ui/page/importbug.php
new file mode 100755
index 0000000000..6aa3121c55
--- /dev/null
+++ b/module/execution/test/ui/page/importbug.php
@@ -0,0 +1,15 @@
+ "//*[@id='table-execution-importbug']/div[2]/div[1]/div/div[1]/div/div",
+ 'firstId' => "//*[@id='table-execution-importbug']/div[2]/div[1]/div/div[1]/div",
+ 'num' => "//*[@id='table-execution-importbug']/div[3]/div[2]/strong",
+ 'saveBtn' => "//*[@id='table-execution-importbug']/div[3]/nav[1]/button"
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/execution/test/ui/page/importtask.php b/module/execution/test/ui/page/importtask.php
new file mode 100755
index 0000000000..0d9532aaf0
--- /dev/null
+++ b/module/execution/test/ui/page/importtask.php
@@ -0,0 +1,15 @@
+ "//*[@id='table-execution-importtask']/div[2]/div[1]/div/div[1]/div/div",
+ 'firstName' => "//*[@id='table-execution-importtask']/div[2]/div[1]/div/div[2]/div/a",
+ 'num' => "//*[@data-page='execution-importtask']/div[1]//li/a/span[2]",
+ 'saveBtn' => "//*[@id='table-execution-importtask']/div[3]/nav[1]/button"
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/execution/test/ui/page/story.php b/module/execution/test/ui/page/story.php
index 9e0b9ba714..1e808b1cbc 100755
--- a/module/execution/test/ui/page/story.php
+++ b/module/execution/test/ui/page/story.php
@@ -5,7 +5,33 @@ class storyPage extends page
{
parent::__construct($webdriver);
$xpath = array(
- 'firstName' => "//*[@id='table-execution-story']/div[2]/div[1]/div/div[2]/div/a",
+ /* 标签 */
+ 'allTab' => "//*[@data-page='execution-story']//div[@id='featureBar']/menu/li[1]/a",
+ 'unclosedTab' => "//*[@data-page='execution-story']//div[@id='featureBar']/menu/li[2]/a",
+ 'draftTab' => "//*[@data-page='execution-story']//div[@id='featureBar']/menu/li[3]/a",
+ 'reviewingTab' => "//*[@data-page='execution-story']//div[@id='featureBar']/menu/li[4]/a",
+ 'num' => "//*[@id='table-execution-story']/div[3]/div[2]/strong[1]",
+ /* 列表 */
+ 'firstCheckbox' => "//*[@id='table-execution-story']/div[2]/div[1]/div/div[1]/div/div",
+ 'firstName' => "//*[@id='table-execution-story']/div[2]/div[1]/div/div[2]/div/a",
+ 'firstPhase' => "//*[@id='table-execution-story']/div[2]/div[2]/div/div[6]/div/span",
+ 'firstAssignTo' => "//*[@id='table-execution-story']/div[2]/div[2]/div/div[7]/div/a/span",
+ 'firstUnlinkBtn' => "//*[@id='table-execution-story']/div[2]/div[3]/div/div/div/nav/a[last()]",
+ /* 批量操作按钮 */
+ 'batchAssignBtn' => "//*[@id='table-execution-story']/div[3]/nav[1]/button[1]",
+ 'assignToAdmin' => "//li//div[text() = 'admin']",
+ 'phaseBtn' => "//*[@id='table-execution-story']/div[3]/nav[1]/button[3]",
+ 'phases' => "//*[@data-page='execution-story']/div[4]/menu/menu",
+ /* 需求指派弹窗 */
+ 'submitBtn' => "//*[@data-name='assignedTo']/../div[3]/div/button",
+ /* 需求估算弹窗 */
+ 'reestimate' => "//*[@id='storyEstimateTable']/../../div/button",
+ 'estimateA' => "//*[@id='storyEstimateTable']/tbody/tr[2]/td[last()]/input",
+ 'estimateB' => "//*[@id='storyEstimateTable']/tbody/tr[3]/td[last()]/input",
+ 'estimateC' => "//*[@id='storyEstimateTable']/tbody/tr[4]/td[last()]/input",
+ 'average' => "//*[@id='storyEstimateTable']/tbody/tr[5]/td[last()]/input",
+ 'saveBtn' => "//*[@id='storyEstimateTable']/../div/button",
+ 'noTeamInfo' => "//*[@id='storyEstimateModal']/div/div/div[3]/div/p/span",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/execution/test/ui/story.php b/module/execution/test/ui/story.php
new file mode 100755
index 0000000000..e1fb72e0b6
--- /dev/null
+++ b/module/execution/test/ui/story.php
@@ -0,0 +1,108 @@
+id->range('1');
+$product->name->range('产品1');
+$product->type->range('normal');
+$product->gen(1);
+
+$project = zenData('project');
+$project->id->range('1-5');
+$project->project->range('0, 1, 1, 0, 4');
+$project->model->range('scrum, []{2}, scrum, []');
+$project->type->range('project, sprint{2}, project, sprint');
+$project->auth->range('extend, []{2}, extend, []');
+$project->storytype->range('`story,epic,requirement`');
+$project->path->range('`,1,`, `,1,2,`, `,1,3,`, `,4,`, `,4,5,`');
+$project->grade->range('1');
+$project->name->range('项目1, 项目1执行1, 项目1执行2, 项目2, 项目2执行1');
+$project->hasProduct->range('1');
+$project->status->range('wait');
+$project->acl->range('open');
+$project->gen(5);
+
+$projectProduct = zenData('projectproduct');
+$projectProduct->project->range('1-5');
+$projectProduct->product->range('1');
+$projectProduct->gen(5);
+
+$story = zenData('story');
+$story->id->range('1-100');
+$story->parent->range('0');
+$story->isParent->range('0');
+$story->root->range('1-15');
+$story->path->range('`,1,`, `,2,`, `,3,`, `,4,`, `,5,`, `,6,`, `,7,`, `,8,`, `,9,`, `,10,`, `,11,`, `,12,`, `,13,`, `,14,`, `,15,`');
+$story->grade->range('1');
+$story->product->range('1');
+$story->module->range('0');
+$story->plan->range('0');
+$story->title->range('1-15');
+$story->type->range('story');
+$story->estimate->range('0');
+$story->status->range('active{3}, closed{3}, reviewing{3}, draft{3}, changing{3}');
+$story->stage->range('projected');
+$story->assignedTo->range('[]');
+$story->version->range('1');
+$story->gen(15);
+
+$storySpec = zenData('storyspec');
+$storySpec->story->range('1-15');
+$storySpec->version->range('1');
+$storySpec->title->range('1-15');
+$storySpec->gen(15);
+
+$projectStory = zenData('projectstory');
+$projectStory->project->range('1{15}, 2{15}');
+$projectStory->product->range('1');
+$projectStory->branch->range('0');
+$projectStory->story->range('1-15, 1-15');
+$projectStory->version->range('1');
+$projectStory->order->range('1{15}, 2{15}');
+$projectStory->gen(30);
+
+$user = zenData('user');
+$user->id->range('1-100');
+$user->dept->range('0');
+$user->account->range('admin, user1, user2');
+$user->realname->range('admin, USER1, USER2');
+$user->password->range('77839ef72f7b71a3815a77d038e267e0');
+$user->gen(3);
+
+$team = zenData('team');
+$team->id->range('1-100');
+$team->root->range('1{3}, 2{3}');
+$team->type->range('project{3}, execution{3}');
+$team->account->range('admin, user1, user2, admin, user1, user2');
+$team->gen(6);
+
+
+$tester = new storyTester();
+$tester->login();
+
+/* 标签统计 */
+r($tester->checkTab('allTab', '15')) && p('message') && e('allTab下显示条数正确'); //检查全部标签下显示条数
+r($tester->checkTab('unclosedTab', '12')) && p('message') && e('unclosedTab下显示条数正确'); //检查未关闭标签下显示条数
+r($tester->checkTab('draftTab', '3')) && p('message') && e('draftTab下显示条数正确'); //检查草稿标签下显示条数
+r($tester->checkTab('reviewingTab', '3')) && p('message') && e('reviewingTab下显示条数正确'); //检查评审中标签下显示条数
+/* 移除需求 */
+r($tester->unlinkStory()) && p('message') && e('需求移除成功'); //移除需求
+r($tester->batchUnlinkStory()) && p('message') && e('需求批量移除成功'); //批量移除需求
+/* 批量编辑阶段 */
+r($tester->batchEditPhase('draft', 'testing')) && p('status,message') && e('success,批量编辑draft阶段成功'); //编辑草稿状态的需求的阶段为测试中
+r($tester->batchEditPhase('reviewing', 'wait')) && p('status,message') && e('success,批量编辑reviewing阶段成功'); //编辑评审中状态的需求的阶段为未开始
+r($tester->batchEditPhase('active', 'verified')) && p('status,message') && e('success,批量编辑active阶段成功'); //编辑激活状态的需求的阶段为已验收
+r($tester->batchEditPhase('changing', 'planned')) && p('status,message') && e('success,批量编辑changing阶段成功'); //编辑变更中状态的需求的阶段为已计划
+r($tester->batchEditPhase('closed', 'rejected')) && p('status,message') && e('success,批量编辑closed阶段成功'); //编辑已关闭状态的需求的阶段为验收失败
+/* 指派 */
+r($tester->assignTo('USER1')) && p('message') && e('指派成功'); //单个指派
+r($tester->batchAssignTo()) && p('message') && e('批量指派成功'); //批量指派
+$tester->closeBrowser();
diff --git a/module/execution/test/ui/storyestimate.php b/module/execution/test/ui/storyestimate.php
new file mode 100755
index 0000000000..0fcb659e8f
--- /dev/null
+++ b/module/execution/test/ui/storyestimate.php
@@ -0,0 +1,105 @@
+id->range('1');
+$product->name->range('产品1');
+$product->type->range('normal');
+$product->gen(1);
+
+$project = zenData('project');
+$project->id->range('1-5');
+$project->project->range('0, 1, 1, 0, 4');
+$project->model->range('scrum, []{2}, scrum, []');
+$project->type->range('project, sprint{2}, project, sprint');
+$project->auth->range('extend, []{2}, extend, []');
+$project->storytype->range('`story,epic,requirement`');
+$project->path->range('`,1,`, `,1,2,`, `,1,3,`, `,4,`, `,4,5,`');
+$project->grade->range('1');
+$project->name->range('项目1, 项目1执行1, 项目1执行2, 项目2, 项目2执行1');
+$project->hasProduct->range('1');
+$project->status->range('wait');
+$project->acl->range('open');
+$project->gen(5);
+
+$projectProduct = zenData('projectproduct');
+$projectProduct->project->range('1-5');
+$projectProduct->product->range('1');
+$projectProduct->gen(5);
+
+$story = zenData('story');
+$story->id->range('1-100');
+$story->parent->range('0');
+$story->isParent->range('0');
+$story->root->range('1-15');
+$story->path->range('`,1,`, `,2,`, `,3,`, `,4,`, `,5,`, `,6,`, `,7,`, `,8,`, `,9,`, `,10,`, `,11,`, `,12,`, `,13,`, `,14,`, `,15,`');
+$story->grade->range('1');
+$story->product->range('1');
+$story->module->range('0');
+$story->plan->range('0');
+$story->title->range('1-15');
+$story->type->range('story');
+$story->estimate->range('0');
+$story->status->range('active{3}, closed{3}, reviewing{3}, draft{3}, changing{3}');
+$story->stage->range('projected');
+$story->assignedTo->range('[]');
+$story->version->range('1');
+$story->gen(2);
+
+$storySpec = zenData('storyspec');
+$storySpec->story->range('1-15');
+$storySpec->version->range('1');
+$storySpec->title->range('1-15');
+$storySpec->gen(15);
+
+$projectStory = zenData('projectstory');
+$projectStory->project->range('1{2}, 2, 3');
+$projectStory->product->range('1');
+$projectStory->branch->range('0');
+$projectStory->story->range('1-2, 1-2');
+$projectStory->version->range('1');
+$projectStory->order->range('1-2, 1{2}');
+$projectStory->gen(4);
+
+$user = zenData('user');
+$user->id->range('1-100');
+$user->dept->range('0');
+$user->account->range('admin, user1, user2');
+$user->realname->range('admin, USER1, USER2');
+$user->password->range('77839ef72f7b71a3815a77d038e267e0');
+$user->gen(3);
+
+$team = zenData('team');
+$team->id->range('1-100');
+$team->root->range('1{3}, 2{3}');
+$team->type->range('project{3}, execution{3}');
+$team->account->range('admin, user1, user2, admin, user1, user2');
+$team->gen(6);
+
+$storyEstimate = zenData('storyestimate');
+$storyEstimate->gen(0);
+
+$estimate = array(
+ array('1', '2', '3', 'averge' => '2'),
+ array('1', '0', '0', 'averge' => '1'),
+ array('a'),
+ array('-1'),
+);
+
+$tester = new storyEstimateTester();
+$tester->login();
+
+r($tester->storyEstimate($estimate[0], '1')) && p('message') && e('估算成功');
+r($tester->storyEstimate($estimate[1], '2')) && p('message') && e('估算成功');
+r($tester->checkErrorInfo($estimate[2], 'notNumber')) && p('message') && e('估算值为非数字提示成功');
+r($tester->checkErrorInfo($estimate[3], 'negative')) && p('message') && e('估算值为负数提示成功');
+r($tester->noTeamInfo()) && p('message') && e('没有团队成员提示成功');
+$tester->closeBrowser();
diff --git a/module/extension/model.php b/module/extension/model.php
index dedd0643ec..211003a719 100644
--- a/module/extension/model.php
+++ b/module/extension/model.php
@@ -678,7 +678,7 @@ class extensionModel extends model
if(!file_exists($file)) continue;
/* 如果没有权限或者删除失败则返回提示信息。 */
- $parentDir = mb_substr($file, 0, strripos($file, '/'));
+ $parentDir = dirname($file);
if(!is_writable($file) || !is_writable($parentDir))
{
$commandTips[] = PHP_OS == 'Linux' ? "sudo rm -fr $file" : "del $file";
@@ -719,7 +719,7 @@ class extensionModel extends model
if(!is_dir($path)) continue;
/* 如果没有权限或者删除失败则返回提示信息。*/
- $parentDir = mb_substr($path, 0, strripos($path, '/'));
+ $parentDir = dirname($path);
if(!is_writable($path) || !is_writable($parentDir))
{
$commandTips[] = PHP_OS == 'Linux' ? "sudo rm -fr $appRoot$dir" : "rmdir $appRoot$dir /s /q";
diff --git a/module/extension/zen.php b/module/extension/zen.php
index 9cfc0847ad..4fb37ef21d 100644
--- a/module/extension/zen.php
+++ b/module/extension/zen.php
@@ -431,15 +431,16 @@ class extensionZen extends extension
else
{
/* 检查插件包里的代码文件的父目录对应禅道目录是否可写。 */
- $parentDir = mb_substr($path, 0, strripos($path, '/'));
- if(is_dir($parentDir) && !is_writable($parentDir))
+ $parentDir = dirname($path);
+ while(!file_exists($parentDir)) $parentDir = dirname($parentDir);
+ if(!is_writable($parentDir))
{
$checkResult->errors .= sprintf($this->lang->extension->errorTargetPathNotWritable, $path) . '
';
$checkResult->chmodCommands .= "sudo chmod -R 777 $path
";
$checkResult->errors .= sprintf($this->lang->extension->errorTargetPathNotExists, $path) . '
';
$checkResult->mkdirCommands .= "sudo mkdir -p $path
";
}
- else if(!mkdir($path, 0777, true))
+ elseif(!mkdir($path, 0777, true))
{
/* 如果目录不存在并且创建目录失败。 */
$checkResult->errors .= sprintf($this->lang->extension->errorTargetPathNotExists, $path) . '
';
diff --git a/module/group/packagemanager.php b/module/group/packagemanager.php
index 0a555ccbe3..ce0df57a2e 100644
--- a/module/group/packagemanager.php
+++ b/module/group/packagemanager.php
@@ -1912,7 +1912,7 @@ $config->group->package->manageCase->privs['testcase-batchChangeBranch'] =
$config->group->package->manageCase->privs['testcase-linkCases'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 12, 'depend' => array('testcase-view'), 'recommend' => array('testcase-create', 'testcase-edit', 'testcase-linkBugs'));
$config->group->package->manageCase->privs['testcase-linkBugs'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 13, 'depend' => array('testcase-view'), 'recommend' => array('testcase-create', 'testcase-edit', 'testcase-linkCases'));
$config->group->package->manageCase->privs['testcase-batchConfirmStoryChange'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 8, 'depend' => array(), 'recommend' => array());
-$config->group->package->manageCase->privs['testcase-batchCaseTypeChange'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 11, 'depend' => array(), 'recommend' => array('testcase-edit'));
+$config->group->package->manageCase->privs['testcase-batchChangeType'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 11, 'depend' => array(), 'recommend' => array('testcase-edit'));
$config->group->package->manageCase->privs['testcase-confirmLibcaseChange'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 14, 'depend' => array('testcase-view'), 'recommend' => array('testcase-confirmChange', 'testcase-confirmStoryChange', 'testcase-create', 'testcase-edit', 'testcase-ignoreLibcaseChange'));
$config->group->package->manageCase->privs['testcase-ignoreLibcaseChange'] = array('edition' => 'open,biz,max,ipd', 'vision' => 'rnd', 'order' => 15, 'depend' => array('testcase-view'), 'recommend' => array('testcase-confirmChange', 'testcase-confirmLibcaseChange', 'testcase-confirmStoryChange', 'testcase-create', 'testcase-edit'));
$config->group->package->manageCase->privs['testcase-submit'] = array('edition' => 'max,ipd', 'vision' => 'rnd', 'order' => 4, 'depend' => array('testcase-view'), 'recommend' => array('testcase-confirmChange', 'testcase-confirmLibcaseChange', 'testcase-confirmStoryChange', 'testcase-create', 'testcase-edit', 'testcase-ignoreLibcaseChange', 'testcase-linkBugs', 'testcase-linkCases'));
@@ -4218,7 +4218,7 @@ $config->group->package->manageThinkWizard->subset = 'thinkwizard';
$config->group->package->manageThinkWizard->privs = array();
$config->group->package->manageThinkWizard->privs['thinkwizard-create'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 5, 'depend' => array('thinkwizard-browse'));
$config->group->package->manageThinkWizard->privs['thinkwizard-edit'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 10, 'depend' => array('thinkwizard-browse'));
-$config->group->package->manageThinkWizard->privs['thinkwizard-design'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 15, 'depend' => array('thinkwizard-browse', 'thinkwizard-result', 'thinkstep-create', 'thinkstep-edit', 'thinkstep-view', 'thinkstep-delete'));
+$config->group->package->manageThinkWizard->privs['thinkwizard-design'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 15, 'depend' => array('thinkwizard-browse', 'thinkwizard-result', 'thinkstep-create', 'thinkstep-edit', 'thinkstep-view', 'thinkstep-delete', 'thinkstep-link', 'thinkstep-cancelLink'));
$config->group->package->manageThinkWizard->privs['thinkwizard-publish'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 20, 'depend' => array('thinkwizard-browse'));
$config->group->package->manageThinkWizard->privs['thinkwizard-offline'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 25, 'depend' => array('thinkwizard-browse'));
$config->group->package->manageThinkWizard->privs['thinkwizard-admin'] = array('edition' => 'ipd', 'vision' => 'or', 'order' => 25, 'depend' => array('thinkwizard-browse'));
diff --git a/module/install/lang/de.php b/module/install/lang/de.php
index f6f8db2d02..97c8cb746a 100644
--- a/module/install/lang/de.php
+++ b/module/install/lang/de.php
@@ -160,6 +160,7 @@ $lang->install->errorTableExists = 'Die Tabellen existieren bereits. Wenn Zen
$lang->install->errorCreateTable = 'Erstellung der Tabellen fehlgeschlagen.';
$lang->install->errorEngineInnodb = 'Your MySQL does not support InnoDB data table engine. Please modify it to MyISAM and try again.';
$lang->install->errorImportDemoData = 'Import der Demodaten fehlgeschlagen.';
+$lang->install->errorDBUserPriv = 'The current database user does not have sufficient permissions! Please switch to the root user or use the following SQL statement to grant the current user permissions:\n';
$lang->install->setConfig = 'Konfigurationsdatei erstellen';
$lang->install->key = 'Eintrag';
diff --git a/module/install/lang/en.php b/module/install/lang/en.php
index 49b5af6972..30133261c2 100644
--- a/module/install/lang/en.php
+++ b/module/install/lang/en.php
@@ -160,6 +160,7 @@ $lang->install->errorTableExists = 'The data table has existed. If ZenTao has
$lang->install->errorCreateTable = 'Failed to create the table.';
$lang->install->errorEngineInnodb = 'Your MySQL does not support InnoDB data table engine. Please modify it to MyISAM and try again.';
$lang->install->errorImportDemoData = 'Failed to import the demo data.';
+$lang->install->errorDBUserPriv = 'The current database user does not have sufficient permissions! Please switch to the root user or use the following SQL statement to grant the current user permissions:\n';
$lang->install->setConfig = 'Create config file';
$lang->install->key = 'Item';
diff --git a/module/install/lang/fr.php b/module/install/lang/fr.php
index 5598de0e70..fb3a0b985d 100644
--- a/module/install/lang/fr.php
+++ b/module/install/lang/fr.php
@@ -160,6 +160,7 @@ $lang->install->errorTableExists = "La base existe. Si ZenTao a été install
$lang->install->errorCreateTable = 'Echec en création de la base.';
$lang->install->errorEngineInnodb = 'Your MySQL does not support InnoDB data table engine. Please modify it to MyISAM and try again.';
$lang->install->errorImportDemoData = "Echec de l'importation des données de démo.";
+$lang->install->errorDBUserPriv = 'The current database user does not have sufficient permissions! Please switch to the root user or use the following SQL statement to grant the current user permissions:\n';
$lang->install->setConfig = 'Créer fichier de configuration';
$lang->install->key = 'Objet';
diff --git a/module/install/lang/zh-cn.php b/module/install/lang/zh-cn.php
index 35f4b4168b..d1c5eb3a78 100644
--- a/module/install/lang/zh-cn.php
+++ b/module/install/lang/zh-cn.php
@@ -160,6 +160,7 @@ $lang->install->errorTableExists = '数据表已经存在,您之前应该
$lang->install->errorCreateTable = '创建表失败';
$lang->install->errorEngineInnodb = '您当前的数据库不支持使用InnoDB数据表引擎,请修改为MyISAM后重试。';
$lang->install->errorImportDemoData = '导入demo数据失败';
+$lang->install->errorDBUserPriv = '当前数据库用户权限不足!\n请切换root用户或使用以下sql语句赋予当前用户权限:\n';
$lang->install->setConfig = '生成配置文件';
$lang->install->key = '配置项';
diff --git a/module/install/zen.php b/module/install/zen.php
index 5af3f5ca62..8d622b8fad 100644
--- a/module/install/zen.php
+++ b/module/install/zen.php
@@ -268,6 +268,14 @@ class installZen extends install
return $return;
}
+ /* 检查数据库用户是否缺少权限。 */
+ $missingPrivs = $this->install->dbh->checkUserPriv();
+ if($missingPrivs)
+ {
+ $missingPrivs = $this->lang->install->errorDBUserPriv . '' . $missingPrivs . '';
+ return $this->send(array('result' => 'fail', 'callback' => "zui.Modal.alert({icon: 'icon-exclamation-sign', size: '600', iconClass: 'text-4xl text-warning', message: {html:'" . str_replace("'", '"', $missingPrivs) . "'}})"));
+ }
+
/* Get database version. */
$version = $this->install->getDatabaseVersion();
diff --git a/module/kanban/model.php b/module/kanban/model.php
index 1044683b3d..5d06adeedf 100755
--- a/module/kanban/model.php
+++ b/module/kanban/model.php
@@ -2746,12 +2746,13 @@ class kanbanModel extends model
$this->dao->insert(TABLE_KANBANCOLUMN)->data($data)->exec();
if(dao::isError()) return false;
- if($type == 'design') $designColumnID = $this->dao->lastInsertId();
- if($type == 'develop') $devColumnID = $this->dao->lastInsertId();
- if($type == 'test') $testColumnID = $this->dao->lastInsertId();
- if($type == 'resolving') $resolvingColumnID = $this->dao->lastInsertId();
+ $columnID = $this->dao->lastInsertId();
+ if($type == 'design') $designColumnID = $columnID;
+ if($type == 'develop') $devColumnID = $columnID;
+ if($type == 'test') $testColumnID = $columnID;
+ if($type == 'resolving') $resolvingColumnID = $columnID;
- $this->addKanbanCell($executionID, $laneID, $this->dao->lastInsertId(), $laneType);
+ $this->addKanbanCell($executionID, $laneID, $columnID, $laneType);
}
return true;
diff --git a/module/message/config.php b/module/message/config.php
index 3fde4bd720..078589dd8a 100644
--- a/module/message/config.php
+++ b/module/message/config.php
@@ -1,9 +1,9 @@
message->objectTypes = array();
$config->message->objectTypes['product'] = array('opened', 'edited', 'closed', 'undeleted');
-if($config->enableER) $config->message->objectTypes['epic'] = array('opened', 'edited', 'commented', 'changed', 'reviewed', 'closed', 'activated', 'assigned');
-if($config->URAndSR) $config->message->objectTypes['requirement'] = array('opened', 'edited', 'commented', 'changed', 'reviewed', 'closed', 'activated', 'assigned');
-$config->message->objectTypes['story'] = array('opened', 'edited', 'commented', 'frombug', 'changed', 'reviewed', 'closed', 'activated', 'assigned');
+if($config->enableER) $config->message->objectTypes['epic'] = array('opened', 'edited', 'commented', 'changed', 'submitreview', 'reviewed', 'closed', 'activated', 'assigned');
+if($config->URAndSR) $config->message->objectTypes['requirement'] = array('opened', 'edited', 'commented', 'changed', 'submitreview', 'reviewed', 'closed', 'activated', 'assigned');
+$config->message->objectTypes['story'] = array('opened', 'edited', 'commented', 'frombug', 'changed', 'submitreview', 'reviewed', 'closed', 'activated', 'assigned');
$config->message->objectTypes['productplan'] = array('opened', 'edited');
$config->message->objectTypes['release'] = array('opened', 'edited', 'published', 'changestatus');
$config->message->objectTypes['project'] = array('opened', 'edited', 'started', 'delayed', 'suspended', 'closed', 'activated', 'undeleted');
diff --git a/module/message/lang/de.php b/module/message/lang/de.php
index fe5517937c..669384ea2e 100644
--- a/module/message/lang/de.php
+++ b/module/message/lang/de.php
@@ -52,6 +52,7 @@ $lang->message->label->undeleted = 'restore';
$lang->message->label->commented = 'comment';
$lang->message->label->activated = 'activate';
$lang->message->label->resolved = 'resolve';
+$lang->message->label->submitreview = 'Submit Review';
$lang->message->label->reviewed = 'review';
$lang->message->label->confirmed = 'confirm Story';
$lang->message->label->frombug = 'convert from Bug';
diff --git a/module/message/lang/en.php b/module/message/lang/en.php
index 79fdab068b..05c4fef21d 100644
--- a/module/message/lang/en.php
+++ b/module/message/lang/en.php
@@ -52,6 +52,7 @@ $lang->message->label->undeleted = 'restore';
$lang->message->label->commented = 'comment';
$lang->message->label->activated = 'activate';
$lang->message->label->resolved = 'resolve';
+$lang->message->label->submitreview = 'Submit Review';
$lang->message->label->reviewed = 'review';
$lang->message->label->confirmed = 'confirm Story';
$lang->message->label->frombug = 'convert from Bug';
diff --git a/module/message/lang/fr.php b/module/message/lang/fr.php
index b7bcb93e18..a729ae22e5 100644
--- a/module/message/lang/fr.php
+++ b/module/message/lang/fr.php
@@ -52,6 +52,7 @@ $lang->message->label->undeleted = 'restore';
$lang->message->label->commented = 'comment';
$lang->message->label->activated = 'activate';
$lang->message->label->resolved = 'resolve';
+$lang->message->label->submitreview = 'Submit Review';
$lang->message->label->reviewed = 'review';
$lang->message->label->confirmed = 'confirm Story';
$lang->message->label->frombug = 'convert from Bug';
diff --git a/module/message/lang/zh-cn.php b/module/message/lang/zh-cn.php
index 962ed0f395..9fa2592506 100644
--- a/module/message/lang/zh-cn.php
+++ b/module/message/lang/zh-cn.php
@@ -52,6 +52,7 @@ $lang->message->label->undeleted = '还原';
$lang->message->label->commented = '备注';
$lang->message->label->activated = '激活';
$lang->message->label->resolved = '解决';
+$lang->message->label->submitreview = '提交评审';
$lang->message->label->reviewed = '评审';
$lang->message->label->confirmed = "确认{$lang->SRCommon}";
$lang->message->label->frombug = "转{$lang->SRCommon}";
diff --git a/module/metric/calc.class.php b/module/metric/calc.class.php
index 9a97e49534..284db04b3b 100644
--- a/module/metric/calc.class.php
+++ b/module/metric/calc.class.php
@@ -695,6 +695,12 @@ class baseCalc
return $actualDays;
}
+ public function getDevAccountList()
+ {
+ global $dao;
+ return $dao->select('account')->from(TABLE_USER)->where('role')->eq('dev')->andWhere('deleted')->eq('0')->fetchPairs();
+ }
+
public function getExecutions()
{
global $dao;
diff --git a/module/metric/calc/execution/hour/consume_of_frombug_task_in_execution.php b/module/metric/calc/execution/hour/consume_of_frombug_task_in_execution.php
index 855ff30db8..c71bd3257c 100644
--- a/module/metric/calc/execution/hour/consume_of_frombug_task_in_execution.php
+++ b/module/metric/calc/execution/hour/consume_of_frombug_task_in_execution.php
@@ -24,13 +24,12 @@ class consume_of_frombug_task_in_execution extends baseCalc
public $dataset = 'getTasks';
- public $fieldList = array('t1.execution', 't1.consumed', 't1.parent', 't1.fromBug', 't5.fromBug as parentFromBug');
+ public $fieldList = array('t1.execution', 't1.consumed', 't1.parent', 't1.fromBug');
public function calculate($row)
{
if($row->parent == '-1') return;
if($row->parent == '0' && $row->fromBug == 0) return;
- if($row->parent > 0 && (empty($row->parentFromBug) || $row->parentFromBug == 0)) return;
if(!isset($this->result[$row->execution])) $this->result[$row->execution] = 0;
$this->result[$row->execution] += $row->consumed;
diff --git a/module/metric/dataset.php b/module/metric/dataset.php
index 71258022b9..bf2d767f40 100644
--- a/module/metric/dataset.php
+++ b/module/metric/dataset.php
@@ -840,8 +840,6 @@ class dataset
$stmt = $this->dao->select($fieldList)->from(TABLE_TASK)->alias('t1')
->leftJoin(TABLE_PROJECT)->alias('t2')->on('t1.execution=t2.id')
->leftJoin(TABLE_PROJECT)->alias('t3')->on('t2.project=t3.id')
- ->leftJoin(TABLE_USER)->alias('t4')->on('t1.openedBy=t4.account')
- ->leftJoin(TABLE_TASK)->alias('t5')->on('t1.parent=t5.id')
->where('t2.type')->in('sprint,kanban,stage')
->andWhere('t1.deleted')->eq('0')
->andWhere('t2.deleted')->eq('0')
diff --git a/module/misc/js/downloadclient.ui.js b/module/misc/js/downloadclient.ui.js
index 8ab8f1b0af..746782ec06 100644
--- a/module/misc/js/downloadclient.ui.js
+++ b/module/misc/js/downloadclient.ui.js
@@ -1,10 +1,10 @@
window.clickSubmit = () =>
{
const os = $('#os').zui('picker').$.state.value;
- loadPage({url : $.createLink('misc', 'downloadClient', "action=getPackage&os=" + os), selector : '#downloadClient', success: getClient});
+ loadPage({url : $.createLink('misc', rawMethod, "action=getPackage&os=" + os), selector : '#downloadClient', success: getClient});
};
-function getClient()
+window.getClient = function()
{
const os = $('#os').val();
const link = $.createLink('misc', 'ajaxGetClientPackage', 'os=' + os);
@@ -24,7 +24,7 @@ function getClient()
if(res.result == 'success')
{
$('#setted').removeClass('hidden');
- const link = $.createLink('misc', 'downloadClient', "action=downloadPackage" + '&os=' + os);
+ const link = $.createLink('misc', rawMethod, "action=downloadPackage" + '&os=' + os);
zui.Modal.hide();
open(link, '_blank');
}
@@ -52,8 +52,7 @@ function getClient()
window.showPackageSize = () =>
{
- const os = $('#os').val();
- const link = $.createLink('misc', 'ajaxGetPackageSize', 'os=' + os);
+ const link = $.createLink('misc', 'ajaxGetPackageSize');
$.getJSON(link, res =>
{
if(res.result == 'success')
diff --git a/module/misc/lang/de.php b/module/misc/lang/de.php
index d26e41d4c5..eb50f48f0d 100644
--- a/module/misc/lang/de.php
+++ b/module/misc/lang/de.php
@@ -114,6 +114,7 @@ $lang->misc->feature->promptExecImage = 'theme/default/images/main/prompt_exec
$lang->misc->feature->promptLearnMore = 'https://www.zentao.net/book/zentaopms/1097.html';
/* Release Date. */
+$lang->misc->releaseDate['20.7.1'] = '2024-09-30';
$lang->misc->releaseDate['20.7'] = '2024-09-14';
$lang->misc->releaseDate['20.6'] = '2024-08-30';
$lang->misc->releaseDate['20.5'] = '2024-08-16';
diff --git a/module/misc/lang/en.php b/module/misc/lang/en.php
index 6a2dab3f8c..d73d3896f7 100644
--- a/module/misc/lang/en.php
+++ b/module/misc/lang/en.php
@@ -114,6 +114,7 @@ $lang->misc->feature->promptExecImage = 'theme/default/images/main/prompt_exec
$lang->misc->feature->promptLearnMore = 'https://www.zentao.net/book/zentaopms/1097.html';
/* Release Date. */
+$lang->misc->releaseDate['20.7.1'] = '2024-09-30';
$lang->misc->releaseDate['20.7'] = '2024-09-14';
$lang->misc->releaseDate['20.6'] = '2024-08-30';
$lang->misc->releaseDate['20.5'] = '2024-08-16';
diff --git a/module/misc/lang/fr.php b/module/misc/lang/fr.php
index 5ac80033bf..d70bb69db8 100644
--- a/module/misc/lang/fr.php
+++ b/module/misc/lang/fr.php
@@ -114,6 +114,7 @@ $lang->misc->feature->promptExecImage = 'theme/default/images/main/prompt_exec
$lang->misc->feature->promptLearnMore = 'https://www.zentao.net/book/zentaopms/1097.html';
/* Release Date. */
+$lang->misc->releaseDate['20.7.1'] = '2024-09-30';
$lang->misc->releaseDate['20.7'] = '2024-09-14';
$lang->misc->releaseDate['20.6'] = '2024-08-30';
$lang->misc->releaseDate['20.5'] = '2024-08-16';
diff --git a/module/misc/lang/zh-cn.php b/module/misc/lang/zh-cn.php
index 68b9cfcb22..8cd2b06e70 100644
--- a/module/misc/lang/zh-cn.php
+++ b/module/misc/lang/zh-cn.php
@@ -114,6 +114,7 @@ $lang->misc->feature->promptExecImage = 'theme/default/images/main/prompt_exec
$lang->misc->feature->promptLearnMore = 'https://www.zentao.net/book/zentaopms/1097.html';
/* Release Date. */
+$lang->misc->releaseDate['20.7.1'] = '2024-09-30';
$lang->misc->releaseDate['20.7'] = '2024-09-14';
$lang->misc->releaseDate['20.6'] = '2024-08-30';
$lang->misc->releaseDate['20.5'] = '2024-08-16';
@@ -236,6 +237,7 @@ $lang->misc->releaseDate['7.1.stable'] = '2015-03-07';
$lang->misc->releaseDate['6.3.stable'] = '2014-11-07';
/* Release Detail. */
+$lang->misc->feature->all['20.7.1'][] = array('title' => '', 'desc' => '');
$lang->misc->feature->all['20.7'][] = array('title' => '新手引导优化;菜单自定义;工作流优化;OR界面增加贡献模块。', 'desc' => '');
$lang->misc->feature->all['20.6'][] = array('title' => '工作流支持配置多界面;审批流支持使用工作流中字段配置条件;修复Bug。', 'desc' => '');
$lang->misc->feature->all['20.5'][] = array('title' => '文档优化;新增23个内置度量项。', 'desc' => '');
diff --git a/module/misc/ui/downloadclient.html.php b/module/misc/ui/downloadclient.html.php
index 9b86e6ba07..f8f1128daa 100644
--- a/module/misc/ui/downloadclient.html.php
+++ b/module/misc/ui/downloadclient.html.php
@@ -11,11 +11,12 @@ declare(strict_types=1);
namespace zin;
modalHeader(set::title($lang->downloadClient));
+jsVar('rawMethod', $app->rawMethod);
formPanel
(
set::id('downloadClient'),
set::actions(false),
- $action == 'check' ? div(set::className('center p-4'), div($errorInfo), div(a(set::className('btn primary btn-wide'), set::href($this->createLink('misc', 'downloadClient', "action=check")), $lang->refresh))) : null,
+ $action == 'check' ? div(set::className('center p-4'), div($errorInfo), div(a(set::className('btn primary btn-wide'), set::href($this->createLink('misc', $app->rawMethod, "action=check")), $lang->refresh))) : null,
$action == 'selectPackage' ? formGroup
(
set::label($lang->misc->client->version),
@@ -50,5 +51,3 @@ formPanel
) : null,
input(set::className('hidden'), set::name('action'), set::value($action))
);
-
-render('modalDialog');
diff --git a/module/mr/control.php b/module/mr/control.php
index e49cecaf65..50cb5edcd1 100644
--- a/module/mr/control.php
+++ b/module/mr/control.php
@@ -78,6 +78,7 @@ class mr extends control
}
elseif($this->app->tab == 'project')
{
+ $this->session->set('project', $objectID);
$this->loadModel('project')->setMenu($objectID);
}
@@ -291,7 +292,7 @@ class mr extends control
$this->mr->deleteByID($MRID);
if(dao::isError()) return $this->sendError(dao::getError());
- return $this->send(array('result' => 'success', 'load' => $this->createLink($this->app->rawModule, 'browse')));
+ return $this->sendSuccess(array('load' => $this->createLink($this->app->rawModule, 'browse')));
}
/**
@@ -384,7 +385,7 @@ class mr extends control
if(isset($compileStatus) and $compileStatus != 'success')
{
- return $this->send(array('result' => 'fail', 'message' => $this->lang->mr->needCI, 'locate' => helper::createLink($this->app->rawModule, 'view', "mr={$MRID}")));
+ return $this->sendError($this->lang->mr->needCI);
}
}
@@ -392,7 +393,7 @@ class mr extends control
{
if($MR->approvalStatus != 'approved')
{
- return $this->send(array('result' => 'fail', 'message' => $this->lang->mr->needApproved, 'locate' => helper::createLink($this->app->rawModule, 'view', "mr={$MRID}")));
+ return $this->sendError($this->lang->mr->needApproved);
}
}
@@ -400,7 +401,7 @@ class mr extends control
if(isset($rawMR->state) and $rawMR->state == 'merged')
{
$this->mr->logMergedAction($MR);
- return $this->send(array('result' => 'success', 'message' => $this->lang->mr->mergeSuccess, 'load' => true));
+ return $this->sendSuccess(array('message' => $this->lang->mr->mergeSuccess, 'load' => true));
}
/* The type of variable `$rawMR->message` is string. This is different with apiCreateMR. */
@@ -410,7 +411,7 @@ class mr extends control
return $this->sendError(sprintf($this->lang->mr->apiError->sudo, $errorMessage));
}
- return $this->send(array('result' => 'fail', 'message' => $this->lang->mr->mergeFailed, 'locate' => helper::createLink($this->app->rawModule, 'view', "mr={$MRID}")));
+ return $this->sendError($this->lang->mr->mergeFailed);
}
/**
@@ -589,8 +590,8 @@ class mr extends control
$this->mr->link($MRID, $productID, 'story', $this->post->stories);
if(dao::isError()) return $this->sendError(dao::getError());
- $link = inlink('link', "MRID=$MRID&type=story&orderBy=$orderBy");
- return $this->send(array('result' => 'success', 'load' => $link, 'closeModal' => true));
+ $link = $this->createLink($this->app->rawModule,'link', "MRID=$MRID&type=story&orderBy=$orderBy");
+ return $this->sendSuccess(array('load' => $link, 'closeModal' => true));
}
$this->loadModel('story');
@@ -647,10 +648,10 @@ class mr extends control
{
$this->mr->link($MRID, $productID, 'bug', $this->post->bugs);
- if(dao::isError()) return $this->send(array('result' => 'fail', 'message' => dao::getError()));
+ if(dao::isError()) return $this->sendError(dao::getError());
- $link = inlink('link', "MRID=$MRID&type=bug&orderBy=$orderBy");
- return $this->send(array('result' => 'success', 'load' => $link, 'closeModal' => true));
+ $link = $this->createLink($this->app->rawModule,'link', "MRID=$MRID&type=bug&orderBy=$orderBy");
+ return $this->sendSuccess(array('load' => $link, 'closeModal' => true));
}
$this->loadModel('bug');
@@ -705,10 +706,10 @@ class mr extends control
if(!empty($_POST['tasks']))
{
$this->mr->link($MRID, $productID, 'task', $this->post->tasks);
- if(dao::isError()) return $this->send(array('result' => 'fail', 'message' => dao::getError()));
+ if(dao::isError()) return $this->sendError(dao::getError());
- $link = inlink('link', "MRID=$MRID&type=task&orderBy=$orderBy");
- return $this->send(array('result' => 'success', 'load' => $link, 'closeModal' => true));
+ $link = $this->createLink($this->app->rawModule,'link', "MRID=$MRID&type=task&orderBy=$orderBy");
+ return $this->sendSuccess(array('load' => $link, 'closeModal' => true));
}
/* Set browse type. */
@@ -766,19 +767,9 @@ class mr extends control
{
$this->mr->unlink($MRID, $productID, $type, $linkID);
- if(dao::isError())
- {
- $response['result'] = 'fail';
- $response['message'] = dao::getError();
- }
- else
- {
- $link = inlink('link', "MRID=$MRID&type=$type");
- $response['result'] = 'success';
- $response['message'] = '';
- $response['load'] = $link;
- }
- return $this->send($response);
+ if(dao::isError()) return $this->sendError(dao::getError());
+
+ return $this->sendSuccess(array('message' => '', 'load' => $this->createLink($this->app->rawModule, 'link', "MRID=$MRID&type=$type")));
}
/**
diff --git a/module/mr/js/diff.ui.js b/module/mr/js/diff.ui.js
index 254eb25e80..9c93909b40 100644
--- a/module/mr/js/diff.ui.js
+++ b/module/mr/js/diff.ui.js
@@ -279,6 +279,9 @@ window.getDiffs = function(fileName)
'code': {'new': '', 'old': ''},
'line': {'new': [], 'old': []}
};
+
+ const newContent = [];
+ const oldContent = [];
$.each(diffs, function(i, diff)
{
if(diff.fileName == fileName)
@@ -292,17 +295,20 @@ window.getDiffs = function(fileName)
{
if(code.type == 'all' || code.type == 'new')
{
- result.code.new += htmlspecialchars_decode(code.line.substring(1)) + "\n";
+ newContent.push(htmlspecialchars_decode(code.line.substring(1)));
result.line.new.push(parseInt(code.newlc));
}
if(code.type == 'all' || code.type == 'old')
{
- result.code.old += htmlspecialchars_decode(code.line.substring(1)) + "\n";
+ oldContent.push(htmlspecialchars_decode(code.line.substring(1)));
result.line.old.push(parseInt(code.oldlc));
}
})
})
+
+ result.code.new = newContent.join('\n');
+ result.code.old = oldContent.join('\n');
return result;
}
});
diff --git a/module/mr/model.php b/module/mr/model.php
index 62ed1bb402..d4379e7118 100644
--- a/module/mr/model.php
+++ b/module/mr/model.php
@@ -13,6 +13,14 @@ declare(strict_types=1);
*/
class mrModel extends model
{
+ public $moduleName = 'mr';
+
+ public function __construct($appName = '')
+ {
+ parent::__construct($appName);
+ if($this->app->rawModule == 'pullreq') $this->moduleName = 'pullreq';
+ }
+
/**
* 获取合并请求列表.
* Get MR list of gitlab project.
@@ -53,9 +61,9 @@ class mrModel extends model
->beginIF($mode == 'creator' && $param != 'all')->andWhere('createdBy')->eq($param)->fi()
->beginIF($filterProjectSql)->andWhere($filterProjectSql)->fi()
->beginIF($repoID)->andWhere('repoID')->eq($repoID)->fi()
- ->beginIF($this->app->rawModule == 'mr')->andWhere('isFlow')->eq('0')->fi()
- ->beginIF($this->app->rawModule == 'pullreq')->andWhere('isFlow')->eq('1')->fi()
- ->beginIF($objectID)->andWhere('executionID')->in($objectID)->fi()
+ ->beginIF($this->moduleName == 'mr')->andWhere('isFlow')->eq('0')->fi()
+ ->beginIF($this->moduleName == 'pullreq')->andWhere('isFlow')->eq('1')->fi()
+ ->beginIF($objectID && $this->moduleName == 'mr')->andWhere('executionID')->in($objectID)->fi()
->orderBy($orderBy)
->page($pager)
->fetchAll('id');
@@ -177,7 +185,7 @@ class mrModel extends model
$MRID = $this->insertMr($MR);
if(dao::isError()) return array('result' => 'fail', 'message' => dao::getError());
- $this->loadModel('action')->create($this->app->rawModule, $MRID, 'opened');
+ $this->loadModel('action')->create($this->moduleName, $MRID, 'opened');
if($MR->needCI && $MR->jobID) $this->execJob($MRID, (int)$MR->jobID);
$rawMR = $this->apiCreateMR($MR->hostID, $MR);
@@ -217,7 +225,7 @@ class mrModel extends model
if(dao::isError()) return array('result' => 'fail', 'message' => dao::getError());
$linkParams = $this->app->tab == 'execution' || $this->app->tab == 'project' ? "repoID=0&mode=status¶m=opened&objectID={$MR->executionID}" : "repoID={$MR->repoID}";
- return array('result' => 'success', 'message' => $this->lang->saveSuccess, 'load' => helper::createLink($this->app->rawModule, 'browse', $linkParams));
+ return array('result' => 'success', 'message' => $this->lang->saveSuccess, 'load' => helper::createLink($this->moduleName, 'browse', $linkParams));
}
/**
@@ -272,7 +280,7 @@ class mrModel extends model
$MRID = $this->insertMr($MR);
if(dao::isError()) return false;
- $this->loadModel('action')->create($this->app->rawModule, $MRID, 'opened');
+ $this->loadModel('action')->create($this->moduleName, $MRID, 'opened');
/* Exec Job */
if($MR->hasNoConflict == '0' && $MR->mergeStatus == 'can_be_merged' && $MR->jobID) $this->execJob($MRID, (int)$MR->jobID);
@@ -328,15 +336,16 @@ class mrModel extends model
$MR = $this->fetchByID($MRID);
$this->linkObjects($MR);
- $actionID = $this->loadModel('action')->create($this->app->rawModule, $MRID, 'edited');
+ $actionID = $this->loadModel('action')->create($this->moduleName, $MRID, 'edited');
$changes = common::createChanges($oldMR, $MR);
if(!empty($changes)) $this->action->logHistory($actionID, $changes);
$this->createMRLinkedAction($MRID, 'editmr', $MR->editedDate);
if(dao::isError()) return array('result' => 'fail', 'message' => dao::getError());
- $linkParams = $this->app->tab == 'execution' ? "repoID=0&mode=status¶m=opened&objectID={$MR->executionID}" : "repoID={$MR->repoID}";
- return array('result' => 'success', 'message' => $needExecJob ? $this->lang->mr->triggeredCI : $this->lang->saveSuccess, 'load' => helper::createLink($this->app->rawModule, 'browse', $linkParams));
+ if($this->session->{$this->app->tab}) $MR->executionID = $this->session->{$this->app->tab};
+ $linkParams = $this->app->tab == 'execution' || $this->app->tab == 'project' ? "repoID=0&mode=status¶m=opened&objectID={$MR->executionID}" : "repoID={$MR->repoID}";
+ return array('result' => 'success', 'message' => $needExecJob ? $this->lang->mr->triggeredCI : $this->lang->saveSuccess, 'load' => helper::createLink($this->moduleName, 'browse', $linkParams));
}
/**
@@ -353,7 +362,7 @@ class mrModel extends model
{
if(empty($actionDate)) $actionDate = helper::now();
- $MRAction = $actionDate . '::' . $this->app->user->account . '::' . helper::createLink($this->app->rawModule, 'view', "mr={$MRID}");
+ $MRAction = $actionDate . '::' . $this->app->user->account . '::' . helper::createLink($this->moduleName, 'view', "mr={$MRID}");
$this->loadModel('action');
foreach(array('story', 'task', 'bug') as $objectType)
@@ -866,8 +875,6 @@ class mrModel extends model
*/
public function approve(object $MR, string $action = 'approve', string $comment = ''): array
{
- $actionID = $this->loadModel('action')->create($this->app->rawModule, $MR->id, $action);
-
if(isset($MR->status) && $MR->status == 'opened')
{
$oldMR = clone $MR;
@@ -877,7 +884,6 @@ class mrModel extends model
if(isset($MR->approvalStatus) && $rawApprovalStatus != $MR->approvalStatus)
{
$changes = common::createChanges($oldMR, $MR);
- $this->action->logHistory($actionID, $changes);
unset($MR->editedDate);
$MR->approver = $this->app->user->account;
@@ -899,10 +905,12 @@ class mrModel extends model
->exec();
if(dao::isError()) return array('result' => 'fail', 'message' => dao::getError());
+ $actionID = $this->loadModel('action')->create($this->moduleName, $MR->id, $action);
+ $this->action->logHistory($actionID, $changes);
return array('result' => 'success', 'message' => $this->lang->saveSuccess, 'closeModal' => true, 'load' => true);
}
}
- return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation, 'load' => helper::createLink($this->app->rawModule, 'view', "mr={$MR->id}"));
+ return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation, 'load' => helper::createLink($this->moduleName, 'view', "mr={$MR->id}"));
}
/**
@@ -915,16 +923,15 @@ class mrModel extends model
*/
public function close(object $MR): array
{
- $link = helper::createLink($this->app->rawModule, 'view', "mr={$MR->id}");
- if($MR->status == 'closed') return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation, 'load' => $link);
+ if($MR->status == 'closed') return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation);
- $actionID = $this->loadModel('action')->create($this->app->rawModule, $MR->id, 'closed');
+ $actionID = $this->loadModel('action')->create($this->moduleName, $MR->id, 'closed');
$rawMR = $this->apiCloseMR($MR->hostID, $MR->targetProject, $MR->mriid);
$changes = common::createChanges($MR, $rawMR);
$this->action->logHistory($actionID, $changes);
- if(isset($rawMR->state) && $rawMR->state == 'closed') return array('result' => 'success', 'message' => $this->lang->mr->closeSuccess, 'load' => $link);
- return array('result' => 'fail', 'message' => $this->lang->fail, 'load' => $link);
+ if(isset($rawMR->state) && $rawMR->state == 'closed') return array('result' => 'success', 'message' => $this->lang->mr->closeSuccess, 'load' => 'reload');
+ return array('result' => 'fail', 'message' => $this->lang->fail);
}
/**
@@ -937,14 +944,13 @@ class mrModel extends model
*/
public function reopen(object $MR): array
{
- $link = helper::createLink($this->app->rawModule, 'view', "mr={$MR->id}");
- if($MR->status == 'opened') return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation, 'load' => $link);
+ if($MR->status == 'opened') return array('result' => 'fail', 'message' => $this->lang->mr->repeatedOperation);
- $this->loadModel('action')->create($this->app->rawModule, $MR->id, 'reopen');
+ $this->loadModel('action')->create($this->moduleName, $MR->id, 'reopen');
$rawMR = $this->apiReopenMR($MR->hostID, $MR->targetProject, $MR->mriid);
- if(!empty($rawMR) && empty($rawMR->message)) return array('result' => 'success', 'message' => $this->lang->mr->reopenSuccess, 'load' => $link);
- return array('result' => 'fail', 'message' => $this->lang->fail, 'load' => $link);
+ if(!empty($rawMR) && empty($rawMR->message)) return array('result' => 'success', 'message' => $this->lang->mr->reopenSuccess, 'load' => 'reload');
+ return array('result' => 'fail', 'message' => $this->lang->fail);
}
/**
@@ -970,7 +976,7 @@ class mrModel extends model
->leftJoin(TABLE_RELATION)->alias('t2')->on('t1.id=t2.BID')
->where('t2.product')->eq($productID)
->andWhere('t2.relation')->eq('interrated')
- ->andWhere('t2.AType')->eq($this->app->rawModule)
+ ->andWhere('t2.AType')->eq($this->moduleName)
->andWhere('t2.AID')->eq($MRID)
->andWhere('t2.BType')->eq($type)
->andWhere('t1.deleted')->eq(0)
@@ -985,14 +991,16 @@ class mrModel extends model
*
* @param int $objectID
* @param string $objectType
+ * @param string $module mr|pullreq
* @access public
* @return array
*/
- public function getLinkedMRPairs(int $objectID, string $objectType = 'story'): array
+ public function getLinkedMRPairs(int $objectID, string $objectType = 'story', string $module = ''): array
{
+ if(!$module) $module = $this->moduleName;
return $this->dao->select("t2.id,t2.title,t2.status")->from(TABLE_RELATION)->alias('t1')
->leftJoin(TABLE_MR)->alias('t2')->on('t1.AID = t2.id')
- ->where('t1.AType')->eq($this->app->rawModule)
+ ->where('t1.AType')->eq($module)
->andWhere('t1.BType')->eq($objectType)
->andWhere('t1.BID')->eq($objectID)
->andWhere('t2.id')->ne(0)
@@ -1019,14 +1027,14 @@ class mrModel extends model
/* Set link action text. */
$user = $this->loadModel('user')->getRealNameAndEmails($MR->createdBy);
- $comment = $MR->createdDate . '::' . zget($user, 'realname', $this->app->user->realname) . '::' . helper::createLink($this->app->rawModule, 'view', "mr={$MR->id}");
+ $comment = $MR->createdDate . '::' . zget($user, 'realname', $this->app->user->realname) . '::' . helper::createLink($this->moduleName, 'view', "mr={$MR->id}");
$this->loadModel('action');
foreach($objects as $objectID)
{
$relation = new stdclass();
$relation->product = $productID;
- $relation->AType = $this->app->rawModule;
+ $relation->AType = $this->moduleName;
$relation->AID = $MRID;
$relation->relation = 'interrated';
$relation->BType = $type;
@@ -1074,7 +1082,7 @@ class mrModel extends model
{
$relation = new stdclass();
$relation->product = $product ? $product->id : 0;
- $relation->AType = $this->app->rawModule;
+ $relation->AType = $this->moduleName;
$relation->AID = $MR->id;
$relation->relation = 'interrated';
$relation->BType = $type;
@@ -1105,13 +1113,13 @@ class mrModel extends model
$this->dao->delete()->from(TABLE_RELATION)
->where('product')->eq($productID)
- ->andWhere('AType')->eq($this->app->rawModule)
+ ->andWhere('AType')->eq($this->moduleName)
->andWhere('AID')->eq($MRID)
->andWhere('BType')->eq($type)
->andWhere('BID')->eq($objectID)
->exec();
- $this->loadModel('action')->create($type, $objectID, 'deletemr', '', helper::createLink($this->app->rawModule, 'view', "mr={$MRID}"));
+ $this->loadModel('action')->create($type, $objectID, 'deletemr', '', helper::createLink($this->moduleName, 'view', "mr={$MRID}"));
return !dao::isError();
}
@@ -1154,7 +1162,7 @@ class mrModel extends model
*/
public function logMergedAction(object $MR): bool
{
- $this->loadModel('action')->create($this->app->rawModule, $MR->id, 'mergedmr');
+ $this->loadModel('action')->create($this->moduleName, $MR->id, 'mergedmr');
$product = $this->getMRProduct($MR);
foreach(array('story', 'bug', 'task') as $type)
@@ -1162,7 +1170,7 @@ class mrModel extends model
$objects = $this->getLinkList($MR->id, $product ? $product->id : 0, $type);
foreach($objects as $object)
{
- $this->action->create($type, $object->id, 'mergedmr', '', helper::createLink($this->app->rawModule, 'view', "mr={$MR->id}"));
+ $this->action->create($type, $object->id, 'mergedmr', '', helper::createLink($this->moduleName, 'view', "mr={$MR->id}"));
}
}
@@ -1271,7 +1279,7 @@ class mrModel extends model
$this->dao->delete()->from(TABLE_MR)->where('id')->eq($MRID)->exec();
- $this->loadModel('action')->create($this->app->rawModule, $MRID, 'deleted', '', $MR->title);
+ $this->loadModel('action')->create($this->moduleName, $MRID, 'deleted', '', $MR->title);
$this->createMRLinkedAction($MRID, 'removemr');
return !dao::isError();
}
@@ -1300,7 +1308,7 @@ class mrModel extends model
$newMR->compileStatus = $compile->status;
if($newMR->compileStatus == 'failure') $newMR->status = 'closed';
if($newMR->compileStatus == 'create_fail') $newMR->status = 'closed';
- $this->loadModel('repo')->saveRelation($MRID, $this->app->rawModule, $compile->id, 'compile', 'mrjob');
+ $this->loadModel('repo')->saveRelation($MRID, 'mr', $compile->id, 'compile', 'mrjob');
$this->dao->update(TABLE_MR)->data($newMR)->where('id')->eq($MRID)->autoCheck()->exec();
return dao::isError();
diff --git a/module/mr/ui/actions.html.php b/module/mr/ui/actions.html.php
index c2dbfc025c..d869ef2741 100644
--- a/module/mr/ui/actions.html.php
+++ b/module/mr/ui/actions.html.php
@@ -19,7 +19,7 @@ $mainActions = array();
$suffixActions = array();
foreach($config->mr->view->operateList as $operate)
{
- if(!common::hasPriv('mr', $operate == 'reject' ? 'approval' : $operate)) continue;
+ if(!common::hasPriv($app->rawModule, $operate == 'reject' ? 'approval' : $operate)) continue;
if($operate == 'reopen' && (!$MR->synced || $rawMR->state != 'closed')) continue;
if(in_array($rawMR->state, array('closed', 'merged')) && $operate == 'accept') continue;
diff --git a/module/mr/ui/browse.html.php b/module/mr/ui/browse.html.php
index cab2235736..79d2005ea0 100644
--- a/module/mr/ui/browse.html.php
+++ b/module/mr/ui/browse.html.php
@@ -17,8 +17,8 @@ dropmenu(set::objectID($repo->id), set::text($repo->name), set::tab('repo'));
foreach($MRList as $MR)
{
/* The user whether has the permission of delete and edit does not require the judge of the permission from the project of the server. */
- $MR->canDelete = hasPriv('mr', 'delete') ? '' : 'disabled';
- $MR->canEdit = hasPriv('mr', 'edit') ? '' : 'disabled';
+ $MR->canDelete = hasPriv($app->rawModule, 'delete') ? '' : 'disabled';
+ $MR->canEdit = hasPriv($app->rawModule, 'edit') ? '' : 'disabled';
if($MR->status == 'merged' || $MR->status == 'closed')
{
@@ -42,12 +42,12 @@ featureBar
$linkParams = $app->tab == 'devops' ? "repoID={$repo->id}" : '';
toolBar
(
- hasPriv('mr', 'create') ? item(set(array
+ hasPriv($app->rawModule, 'create') ? item(set(array
(
'text' => $lang->mr->create,
'icon' => 'plus',
'class' => 'btn primary',
- 'url' => createLink('mr', 'create', $linkParams)
+ 'url' => createLink($app->rawModule, 'create', $linkParams)
))) : null
);
@@ -56,7 +56,7 @@ dtable
set::userMap($users),
set::cols($config->mr->dtable->fieldList),
set::data($MRs),
- set::sortLink(createLink('mr', 'browse', "repoID={$repo->id}&mode={$mode}¶m={$param}&objectID={$objectID}&orderBy={name}_{sortType}&recTotal={$pager->recTotal}&recPerPage={$pager->recPerPage}")),
+ set::sortLink(createLink($app->rawModule, 'browse', "repoID={$repo->id}&mode={$mode}¶m={$param}&objectID={$objectID}&orderBy={name}_{sortType}&recTotal={$pager->recTotal}&recPerPage={$pager->recPerPage}")),
set::orderBy($orderBy),
set::footPager(usePager())
);
diff --git a/module/mr/ui/browsebyexecution.html.php b/module/mr/ui/browsebyexecution.html.php
index e0c86f643f..bbe319f321 100644
--- a/module/mr/ui/browsebyexecution.html.php
+++ b/module/mr/ui/browsebyexecution.html.php
@@ -25,8 +25,8 @@ foreach($MRList as $index => $MR)
$repo = $repoList[$MR->repoID];
/* The user whether has the permission of delete and edit does not require the judge of the permission from the project of the server. */
- $MR->canDelete = hasPriv('mr', 'delete') ? '' : 'disabled'; /* The value can be '' or 'disabled', 'disabled' means that user can NOT do this. */
- $MR->canEdit = hasPriv('mr', 'edit') ? '' : 'disabled';
+ $MR->canDelete = hasPriv($app->rawModule, 'delete') ? '' : 'disabled'; /* The value can be '' or 'disabled', 'disabled' means that user can NOT do this. */
+ $MR->canEdit = hasPriv($app->rawModule, 'edit') ? '' : 'disabled';
if($MR->status == 'merged' || $MR->status == 'closed')
{
@@ -64,11 +64,11 @@ featureBar
toolBar
(
- hasPriv('mr', 'create') ? item(
+ hasPriv($app->rawModule, 'create') ? item(
set::text($lang->mr->create),
set::icon('plus'),
set::className('btn primary'),
- set::url(createLink('mr', 'create', "repoID=" . ($repoID ? $repoID : key($repoList)) . "&objectID={$objectID}")),
+ set::url(createLink($app->rawModule, 'create', "repoID=" . ($repoID ? $repoID : key($repoList)) . "&objectID={$objectID}")),
set('data-app', $app->tab)
) : null
);
@@ -78,7 +78,7 @@ dtable
set::userMap($users),
set::cols($config->mr->dtable->fieldList),
set::data($MRs),
- set::sortLink(createLink('mr', 'browse', "repoID={$repoID}&mode={$mode}¶m={$param}&objectID={$objectID}&orderBy={name}_{sortType}&recTotal={$pager->recTotal}&recPerPage={$pager->recPerPage}")),
+ set::sortLink(createLink($app->rawModule, 'browse', "repoID={$repoID}&mode={$mode}¶m={$param}&objectID={$objectID}&orderBy={name}_{sortType}&recTotal={$pager->recTotal}&recPerPage={$pager->recPerPage}")),
set::orderBy($orderBy),
set::footPager(usePager())
);
diff --git a/module/mr/ui/create.html.php b/module/mr/ui/create.html.php
index f85b3c07ff..1468401b51 100644
--- a/module/mr/ui/create.html.php
+++ b/module/mr/ui/create.html.php
@@ -188,7 +188,7 @@ formPanel
'text' => $lang->goback,
'class' => 'btn',
'data-app' => $app->tab,
- 'url' => createLink('mr', 'browse', "repoID=" . ($executionID ? 0 : $repo->id) . "&mode=status¶m=opened&objectID={$executionID}")
+ 'url' => createLink($app->rawModule, 'browse', "repoID=" . ($executionID ? 0 : $repo->id) . "&mode=status¶m=opened&objectID={$executionID}")
)
))
);
diff --git a/module/mr/ui/header.html.php b/module/mr/ui/header.html.php
index 42bf282692..6c8cdf92ff 100644
--- a/module/mr/ui/header.html.php
+++ b/module/mr/ui/header.html.php
@@ -14,6 +14,7 @@ $headers = nav
(
$lang->mr->view,
set::href(createLink($moduleName, 'view', "MRID={$MR->id}")),
+ set('data-app', $app->tab),
$methodName == 'view' ? setClass('active') : null
)
),
diff --git a/module/mr/ui/view.html.php b/module/mr/ui/view.html.php
index 8a145348d3..e939502325 100644
--- a/module/mr/ui/view.html.php
+++ b/module/mr/ui/view.html.php
@@ -86,7 +86,6 @@ else
detailHeader
(
- set::back('mr-browse'),
to::title
(
entityLabel
@@ -206,7 +205,7 @@ panel
history
(
set::objectID($MR->id),
- set::commentUrl(createLink('action', 'comment', array('objectType' => 'mr', 'objectID' => $MR->id)))
+ set::commentUrl(createLink('action', 'comment', array('objectType' => $app->rawModule, 'objectID' => $MR->id)))
)
)
),
diff --git a/module/pipeline/model.php b/module/pipeline/model.php
index 0563086285..130d650571 100755
--- a/module/pipeline/model.php
+++ b/module/pipeline/model.php
@@ -87,7 +87,7 @@ class pipelineModel extends model
public function getPairs(string $type = '', bool $checkOnline = false): array
{
$type = strtolower($type);
- if(($this->config->inQuickon && $this->config->inQuickon !== 'false') || !$checkOnline)
+ if(!$this->config->inQuickon || !$checkOnline)
{
return $this->dao->select('id,name')->from(TABLE_PIPELINE)
->where('deleted')->eq('0')
diff --git a/module/pivot/js/preview.ui.js b/module/pivot/js/preview.ui.js
index 7697df9357..291c3d2d74 100644
--- a/module/pivot/js/preview.ui.js
+++ b/module/pivot/js/preview.ui.js
@@ -19,7 +19,7 @@ function loadBugCreate()
const execution = $('#conditions').find('[name=execution]').val();
const params = window.btoa('begin=' + begin + '&end=' + end + '&product=' + +product + '&execution=' + +execution);
const link = $.createLink('pivot', 'preview', 'dimensionID=' + dimensionID + '&groupID=' + groupID + '&method=bugCreate¶ms=' + params);
- loadPage(link, '#table-pivot-preview');
+ loadPage(link, '#pivotPanel');
}
/**
@@ -44,7 +44,7 @@ function loadProductSummary()
const params = window.btoa('conditions=' + conditions + '&productID=' + productID + '&productStatus=' + productStatus + '&productType=' + productType);
const link = $.createLink('pivot', 'preview', 'dimensionID=' + dimensionID + '&groupID=' + groupID + '&method=productSummary¶ms=' + params);
- loadPage(link, '#table-pivot-preview');
+ loadPage(link, '#pivotPanel');
}
/**
@@ -60,7 +60,7 @@ function loadProjectDeviation()
const end = $('#conditions').find('[name="end"]').val().replaceAll('-', '');
const params = window.btoa('begin=' + begin + '&end=' + end);
const link = $.createLink('pivot', 'preview', 'dimensionID=' + dimensionID + '&groupID=' + groupID + '&method=projectdeviation¶ms=' + params);
- loadPage(link, '#table-pivot-preview,#pivotChart');
+ loadPage(link, '#pivotPanel,#pivotChart');
}
/**
@@ -83,7 +83,7 @@ function loadWorkload()
const params = window.btoa('begin=' + begin.replaceAll('-', '') + '&end=' + end.replaceAll('-', '') + '&days=' + days + '&workhour=' + +workhour + '&dept=' + dept + '&assign=' + assign);
const link = $.createLink('pivot', 'preview', 'dimensionID=' + dimensionID + '&groupID=' + groupID + '&method=workload¶ms=' + params);
- loadPage(link, '#table-pivot-preview');
+ loadPage(link, '#pivotPanel');
}
function toggleShowMode(showMode = 'group')
diff --git a/module/pivot/lang/en.php b/module/pivot/lang/en.php
index b0c8374c2a..6651729fbd 100644
--- a/module/pivot/lang/en.php
+++ b/module/pivot/lang/en.php
@@ -419,6 +419,7 @@ $lang->pivot->stepDesign->columnsTip = 'Add 1 column to the pivot table and set
$lang->pivot->stepDesign->columnTotal = 'Show column totals';
$lang->pivot->stepDesign->columnCalc = 'Summary calculation';
+$lang->pivot->stepDesign->columnPosition = 'Summary position';
$lang->pivot->stepDesign->columnTotalTip = 'Add a row to display the summary data for each column.';
$lang->pivot->stepDesign->total = 'Total';
diff --git a/module/pivot/lang/fr.php b/module/pivot/lang/fr.php
index b5df4c51c0..6c64604e7a 100644
--- a/module/pivot/lang/fr.php
+++ b/module/pivot/lang/fr.php
@@ -419,6 +419,7 @@ $lang->pivot->stepDesign->columnsTip = 'Add 1 column to the pivot table and set
$lang->pivot->stepDesign->columnTotal = 'Show column totals';
$lang->pivot->stepDesign->columnCalc = 'Summary calculation';
+$lang->pivot->stepDesign->columnPosition = 'Summary position';
$lang->pivot->stepDesign->columnTotalTip = 'Add a row to display the summary data for each column.';
$lang->pivot->stepDesign->total = 'Total';
diff --git a/module/product/model.php b/module/product/model.php
index 3a20a3af94..404a760bf4 100755
--- a/module/product/model.php
+++ b/module/product/model.php
@@ -1578,6 +1578,8 @@ class productModel extends model
public function deleteLine(int $lineID): bool
{
$this->dao->update(TABLE_MODULE)->set('deleted')->eq(1)->where('id')->eq($lineID)->exec();
+ $this->loadModel('action')->create('productline', $lineID, 'deleted', '', ACTIONMODEL::CAN_UNDELETED);
+
$this->dao->update(TABLE_PRODUCT)->set('line')->eq('0')->where('line')->eq($lineID)->exec();
return !dao::isError();
diff --git a/module/product/test/ui/page/browse.php b/module/product/test/ui/page/browse.php
index 1d6cef6c01..cc7c0cb844 100644
--- a/module/product/test/ui/page/browse.php
+++ b/module/product/test/ui/page/browse.php
@@ -8,6 +8,8 @@ class browsePage extends page
$xpath = array(
'settings' => "//*[@id='navbar']//a[@data-id='settings']/span",
'browseStoryName' => "//*[@id='stories']/div[2]/div[1]/div/div[2]/div/a",
+ 'firstSelect' => "//*[@id='stories']/div[2]/div[1]/div/div[1]/div/div",
+ 'batchEdit' => "//*[@id='stories']/div[3]/nav[1]/nav/button[1]",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/product/ui/browse.html.php b/module/product/ui/browse.html.php
index ce90c38a99..f40803d285 100644
--- a/module/product/ui/browse.html.php
+++ b/module/product/ui/browse.html.php
@@ -140,7 +140,7 @@ $fnBuildCreateStoryButton = function() use ($lang, $product, $isProjectStory, $s
set::text($createBtnTitle),
set::url($createBtnLink)
),
- dropdown
+ empty($items) ? null : dropdown
(
btn(setClass('dropdown-toggle'), setClass($app->tab != 'product' ? 'secondary' : 'primary'), setStyle(array('padding' => '6px', 'border-radius' => '0 2px 2px 0'))),
set::placement('bottom-end'),
diff --git a/module/product/zen.php b/module/product/zen.php
index ea7ca94d4b..4e72ca485d 100644
--- a/module/product/zen.php
+++ b/module/product/zen.php
@@ -299,7 +299,7 @@ class productZen extends product
if($programID and strpos(",{$hasPrivPrograms},", ",{$programID},") === false) $fields['program']['control'] = 'hidden';
if(isset($fields['program']) and !isset($fields['program']['options'][$programID]) and $programID)
{
- $program = $this->program->getByID($programID);
+ $program = $this->loadModel('program')->getByID($programID);
$fields['program']['options'] += array($programID => $program->name);
}
diff --git a/module/productplan/js/batchedit.ui.js b/module/productplan/js/batchedit.ui.js
index df6b5b16cb..c7e3c4f409 100644
--- a/module/productplan/js/batchedit.ui.js
+++ b/module/productplan/js/batchedit.ui.js
@@ -8,7 +8,7 @@ window.renderRowData = function($row, index, plan)
if($branch.length > 0)
{
- let branchOptions = {name: 'branch', 'multiple': true, defaultValue: plan.branch, onChange: function(){getConflictStories(index)}, 'items': branchPickerItems};
+ let branchOptions = {name: 'branch[' + plan.id + ']', 'multiple': true, defaultValue: plan.branch, onChange: function(){getConflictStories(index)}, 'items': branchPickerItems};
if(plan.parent > 0 && typeof parentBranches[plan.parent] != 'undefined') branchOptions = $.extend({}, branchOptions, {items: parentBranches[plan.parent]});
$row.find('[data-name="branch"]').find('.picker-box').on('inited', function(e, info)
{
diff --git a/module/productplan/model.php b/module/productplan/model.php
index 0e87d20499..0ed9ef67b9 100644
--- a/module/productplan/model.php
+++ b/module/productplan/model.php
@@ -213,7 +213,7 @@ class productplanModel extends model
if(is_string($branch)) $branch = array_unique(explode(',', trim($branch, ',')));
if(is_array($branch) && !empty($branch))
{
- if(count($branch) == 1) $branchQuery = "t1.branch = '" . current($branch) . "'";
+ if(count($branch) == 1) $branchQuery = "FIND_IN_SET('$branch[0]', t1.branch)";
if(count($branch) > 1)
{
foreach($branch as $key => $branchID) $branch[$key] = "FIND_IN_SET('$branchID', t1.branch)";
diff --git a/module/productplan/test/lib/browse.ui.class.php b/module/productplan/test/lib/browse.ui.class.php
index 2d35517475..430eaa8987 100644
--- a/module/productplan/test/lib/browse.ui.class.php
+++ b/module/productplan/test/lib/browse.ui.class.php
@@ -45,4 +45,38 @@ class browseTester extends tester
return ($browsePage->dom->allTab) ? $this->success('成功切换到列表模式') : $this->failed('切换到列表模式失败');
}
}
+
+ /**
+ * 看板中计划排序
+ * sort in kanban
+ * @param $planurl 产品ID
+ * @param $orderBy 排序方式
+ *
+ * @return mixed
+ */
+ public function sortInKanban($planurl, $orderBy)
+ {
+ $browsePage = $this->initForm('productplan', 'browse', $planurl, 'appIframe-product');
+ $browsePage->dom->kanbanBtn->click();//点击进入看板模式
+ $browsePage->dom->orderByBtn->click();
+ $orderButtons = [
+ 'begin_desc' => 'beginDesc',
+ 'begin_asc' => 'beginAsc',
+ ];
+ $browsePage->wait(2);
+ $browsePage->dom->{$orderButtons[$orderBy]}->click();//点击对应的排序方式
+ $browsePage->wait(2);
+ $firBeginToEnd = $browsePage->dom->firBeginToEnd->getText(); // 第一个计划卡片中计划的开始结束时间
+ $secBeginToEnd = $browsePage->dom->secBeginToEnd->getText(); // 第二个计划卡片中计划的开始结束时间
+ $firBegin = substr($firBeginToEnd, 0, strpos($firBeginToEnd, " {$this->lang->productplan->to} ")); // 第一个计划的开始时间
+ $secBegin = substr($secBeginToEnd, 0, strpos($secBeginToEnd, " {$this->lang->productplan->to} ")); // 第二个计划的开始时间
+ if ($orderBy === 'begin_desc')
+ {
+ return ($firBegin > $secBegin) ? $this->success("按计划开始时间倒序排序成功") : $this->failed("按计划开始时间倒序排序失败");
+ }
+ if ($orderBy === 'begin_asc')
+ {
+ return ($firBegin < $secBegin) ? $this->success("按计划开始时间正序排序成功") : $this->failed("按计划开始时间正序排序失败");
+ }
+ }
}
diff --git a/module/productplan/test/ui/page/browse.php b/module/productplan/test/ui/page/browse.php
old mode 100755
new mode 100644
index efac12e533..e60d9d22d0
--- a/module/productplan/test/ui/page/browse.php
+++ b/module/productplan/test/ui/page/browse.php
@@ -33,7 +33,11 @@ class browsePage extends page
'closedNum' => "//*[@id='featureBar']/menu/li[6]/a/span[2]",
'listBtn' => "//button[@data-type='list']",
'kanbanBtn' => "//button[@data-type='kanban']",
- 'orderByBtn' => "//*[@id='actionBar']/button",
+ 'orderByBtn' => "//*[@id='actionBar']/button",//看板中的排序按钮
+ 'beginDesc' => "/html/body/div[3]/menu/menu/li[1]",//计划开始时间倒序
+ 'beginAsc' => "/html/body/div[3]/menu/menu/li[2]",//计划开始时间正序
+ 'firBeginToEnd' => "//div[@class='card-footer']/div/div/span[2]",//第一个计划卡片中的开始时间到结束时间
+ 'secBeginToEnd' => "(//div[@class='card-footer'])[2]/div/div/span[2]",//第二个计划卡片中的开始时间到结束时间
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/productplan/test/ui/sortinkanban.php b/module/productplan/test/ui/sortinkanban.php
new file mode 100755
index 0000000000..18a5648fe6
--- /dev/null
+++ b/module/productplan/test/ui/sortinkanban.php
@@ -0,0 +1,41 @@
+#!/usr/bin/env php
+loadYaml('product', false, 2)->gen(10);
+$productplan = zenData('productplan');
+$productplan->id->range('1-7');
+$productplan->product->range(1);
+$productplan->title->range('计划1,计划2,计划3,计划4,计划5,计划6,计划7');
+$productplan->parent->range(0);
+$productplan->begin->range('`2024-09-19`,`2024-09-20`,`2024-09-21`,`2024-09-22`,`2024-09-23`,`2024-09-24`,`2024-09-25`');
+$productplan->end->range('`2024-10-19`,`2024-10-20`,`2024-10-21`,`2024-10-22`,`2024-10-23`,`2024-10-24`,`2024-10-25`');
+$productplan->status->range('wait{3},doing{2},done{1},closed{1}');
+$productplan->gen(7);
+
+$tester = new browseTester();
+$tester->login();
+$planurl['productID'] = 1;
+
+$orderBy = 'begin_desc';
+r($tester->sortInKanban($planurl, $orderBy)) && p('message,status') && e('按计划开始时间倒序排序成功,SUCCESS');//按计划开始时间倒序进行排序
+
+$orderBy = 'begin_asc';
+r($tester->sortInKanban($planurl, $orderBy)) && p('message,status') && e('按计划开始时间正序排序成功,SUCCESS');//按计划开始时间正序进行排序
+$tester->closeBrowser();
diff --git a/module/project/js/common.ui.js b/module/project/js/common.ui.js
index 0182010b1b..434cabaa78 100644
--- a/module/project/js/common.ui.js
+++ b/module/project/js/common.ui.js
@@ -203,7 +203,7 @@ function checkBudget()
checkProjectInfo();
}
-function checkProjectInfo()
+window.checkProjectInfo = function()
{
const programID = $('[name=parent]').val();
if(programID == 0)
@@ -222,8 +222,9 @@ function checkProjectInfo()
$.getJSON($.createLink('project', 'ajaxGetProjectFormInfo', 'objectType=project&objectID=' + currentProject + "&selectedProgramID=" + programID), function(data)
{
let dateTip = '';
+ let projectEnd = $('[name=longTime]').prop('checked') ? LONG_TIME : $('[name=end]').val();
if(typeof(data.selectedProgramBegin) != 'undefined' && $('[name=begin]').val() != '' && $('[name=begin]').val() < data.selectedProgramBegin) dateTip += beginLessThanParent.replace('%s', data.selectedProgramBegin);
- if(typeof(data.selectedProgramEnd) != 'undefined' && $('[name=end]').val() != '' && $('[name=end]').val() > data.selectedProgramEnd) dateTip += endGreatThanParent.replace('%s', data.selectedProgramEnd);
+ if(typeof(data.selectedProgramEnd) != 'undefined' && projectEnd != '' && projectEnd > data.selectedProgramEnd) dateTip += endGreatThanParent.replace('%s', data.selectedProgramEnd);
if(dateTip != '')
{
$('#dateTip').html(dateTip);
diff --git a/module/project/lang/de.php b/module/project/lang/de.php
index adf57cd6bb..0a772c490c 100644
--- a/module/project/lang/de.php
+++ b/module/project/lang/de.php
@@ -242,7 +242,7 @@ $lang->project->unlinkExecutionMember = "The user participated in %s executions
$lang->project->unlinkExecutionMembers = "The team members you are removing are also in the execution team of this {$lang->projectCommon}. Do you want to remove them from the execution team too?";
$lang->project->productTip = "After clicking New {$lang->productCommon}, the {$lang->projectCommon} will not be linked to the selected {$lang->productCommon}.";
$lang->project->noDevStage = "There is no R&D stage under this {$lang->projectCommon}, or you do not have access permissions. The creation of builds is not supported at the moment.";
-$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the parent program: . ";
+$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the program: . ";
$lang->project->disabledInputTip = 'Please cancel %s first';
$lang->project->linkRepoFailed = "Failed to link {$lang->projectCommon}s and code repositories.";
$lang->project->unLinkProductTip = 'Are you sure you want to unlink %s? (Does not affect linked requirements)';
diff --git a/module/project/lang/en.php b/module/project/lang/en.php
index adf57cd6bb..0a772c490c 100644
--- a/module/project/lang/en.php
+++ b/module/project/lang/en.php
@@ -242,7 +242,7 @@ $lang->project->unlinkExecutionMember = "The user participated in %s executions
$lang->project->unlinkExecutionMembers = "The team members you are removing are also in the execution team of this {$lang->projectCommon}. Do you want to remove them from the execution team too?";
$lang->project->productTip = "After clicking New {$lang->productCommon}, the {$lang->projectCommon} will not be linked to the selected {$lang->productCommon}.";
$lang->project->noDevStage = "There is no R&D stage under this {$lang->projectCommon}, or you do not have access permissions. The creation of builds is not supported at the moment.";
-$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the parent program: . ";
+$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the program: . ";
$lang->project->disabledInputTip = 'Please cancel %s first';
$lang->project->linkRepoFailed = "Failed to link {$lang->projectCommon}s and code repositories.";
$lang->project->unLinkProductTip = 'Are you sure you want to unlink %s? (Does not affect linked requirements)';
diff --git a/module/project/lang/fr.php b/module/project/lang/fr.php
index adf57cd6bb..0a772c490c 100644
--- a/module/project/lang/fr.php
+++ b/module/project/lang/fr.php
@@ -242,7 +242,7 @@ $lang->project->unlinkExecutionMember = "The user participated in %s executions
$lang->project->unlinkExecutionMembers = "The team members you are removing are also in the execution team of this {$lang->projectCommon}. Do you want to remove them from the execution team too?";
$lang->project->productTip = "After clicking New {$lang->productCommon}, the {$lang->projectCommon} will not be linked to the selected {$lang->productCommon}.";
$lang->project->noDevStage = "There is no R&D stage under this {$lang->projectCommon}, or you do not have access permissions. The creation of builds is not supported at the moment.";
-$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the parent program: . ";
+$lang->project->budgetOverrun = "The {$lang->projectCommon}'s budget exceeds the remaining budget of the program: . ";
$lang->project->disabledInputTip = 'Please cancel %s first';
$lang->project->linkRepoFailed = "Failed to link {$lang->projectCommon}s and code repositories.";
$lang->project->unLinkProductTip = 'Are you sure you want to unlink %s? (Does not affect linked requirements)';
diff --git a/module/project/lang/zh-cn.php b/module/project/lang/zh-cn.php
index f14565d338..821bb813c7 100644
--- a/module/project/lang/zh-cn.php
+++ b/module/project/lang/zh-cn.php
@@ -242,7 +242,7 @@ $lang->project->unlinkExecutionMember = "该用户参与了%s%s%s个{$lang->exe
$lang->project->unlinkExecutionMembers = "移除的团队成员还参与了{$lang->projectCommon}下的执行,是否同步从执行团队中移除?";
$lang->project->productTip = "点击新建{$lang->productCommon}后,{$lang->projectCommon}将不会关联已选中的{$lang->productCommon}。";
$lang->project->noDevStage = "该{$lang->projectCommon}下没有研发类型的阶段,或者您没有权限访问,暂时不支持创建版本。";
-$lang->project->budgetOverrun = "{$lang->projectCommon}的预算超出了父项目集的剩余预算:%s。";
+$lang->project->budgetOverrun = "{$lang->projectCommon}的预算超出了项目集的剩余预算:%s。";
$lang->project->disabledInputTip = '请先取消%s';
$lang->project->linkRepoFailed = '关联代码库失败';
$lang->project->unLinkProductTip = "您确认要取消与%s的关联关系吗?(不影响已关联的需求)";
diff --git a/module/project/test/lib/browsetab.ui.class.php b/module/project/test/lib/browsetab.ui.class.php
new file mode 100644
index 0000000000..562836d2c2
--- /dev/null
+++ b/module/project/test/lib/browsetab.ui.class.php
@@ -0,0 +1,25 @@
+initForm('project', 'browse', '', 'appIframe-project');
+ $tabs = array('all', 'undone', 'wait', 'doing');
+ if(!in_array($tab, $tabs)) $form->dom->moreTab->click();
+ $form->wait(2);
+ $form->dom->$tab->click();
+ $form->wait(2);
+ /*添加断言,判断标签下条数是否符合预期*/
+ if($form->dom->num->getText() == $expectNum) return $this->success($tab . '标签下条数显示正确');
+ return $this->failed($tab . '标签下条数显示不正确');
+ }
+}
diff --git a/module/project/test/lib/createguide.ui.class.php b/module/project/test/lib/createguide.ui.class.php
new file mode 100644
index 0000000000..74bc33b459
--- /dev/null
+++ b/module/project/test/lib/createguide.ui.class.php
@@ -0,0 +1,23 @@
+initForm('project', 'browse');
+ $form->dom->createProjectBtn->click();
+ $form->dom->$type->click();
+ $form->wait(3);
+
+ //向导弹窗中点击项目管理方式后,跳转是否正确
+ if(strpos($this->response('url'), 'model='.$type)) return $this->success($type.'向导跳转正确');
+ return $this->failed($type.'向导跳转不正确');
+ }
+}
diff --git a/module/project/test/lib/group.ui.class.php b/module/project/test/lib/group.ui.class.php
new file mode 100644
index 0000000000..5a53c95363
--- /dev/null
+++ b/module/project/test/lib/group.ui.class.php
@@ -0,0 +1,50 @@
+initForm('project', 'group', array('projectID' => '1'), 'appIframe-project');
+ $form->dom->createGroupBtn->click();
+ if(isset($project['groupname'])) $form->dom->groupName->setValue($project['groupname']);
+ if(isset($project['groupdesc'])) $form->dom->groupDesc->setValue($project['groupdesc']);
+
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(2);
+ return $this->checkResult($project, $form);
+ }
+
+ /**
+ * Check the result after creating the project group.
+ *
+ * @param array $project
+ * @access public
+ * @return object
+ */
+ public function checkResult($project, $form)
+ {
+ /*检查创建分组弹窗中的提示信息是否正确*/
+ if($form->dom->nameTip)
+ {
+ $nameTipform = $form->dom->nameTip->getText();
+ $nameTip = sprintf($this->lang->error->notempty, $this->lang->group->name);
+ return ($nameTipform == $nameTip) ? $this->success('项目创建分组提示信息正确') : $this->failed('项目创建分组提示信息不正确');
+ }
+ /*创建项目分组后检查列表页的名称和描述是否正确*/
+ else if($form->dom->nameTip === false)
+ {
+ $groupPage = $this->loadPage('project', 'group');
+ if($groupPage->dom->groupNameList->getText() != $project['groupname']) return $this->failed('分组名称错误');
+ if($groupPage->dom->groupDescList->getText() != $project['groupdesc']) return $this->failed('分组描述错误');
+
+ return $this->success('项目分组创建成功');
+ }
+ }
+}
diff --git a/module/project/test/lib/manageproducts.ui.class.php b/module/project/test/lib/manageproducts.ui.class.php
new file mode 100644
index 0000000000..e1963272b8
--- /dev/null
+++ b/module/project/test/lib/manageproducts.ui.class.php
@@ -0,0 +1,62 @@
+initForm('project', 'manageproducts', array('project' => 11), 'appIframe-project');
+ $form->dom->linkBtn->click(); //点击关联其他产品
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(1);
+ if($form->dom->alertModal('text') === '『产品』不能为空。') return $this->success('关联其他产品必填提示信息正确');
+ return $this->failed('关联其他产品必填提示信息不正确');
+ }
+ /**
+ * 关联产品。
+ * Link Products.
+ *
+ * @param array $project
+ * @access public
+ * @return void
+ */
+ public function linkProducts($project)
+ {
+ $form = $this->initForm('project', 'manageproducts', array('project' => 11), 'appIframe-project');
+ $form->dom->linkBtn->click(); //点击关联其他产品
+ if(isset($project['otherProducts'])) $form->dom->{'otherProducts[]'}->multiPicker($project['otherProducts']);
+ $form->dom->btn($this->lang->save)->click();
+
+ //跳转到项目概况页检查已关联产品
+ $form = $this->initForm('project', 'view', array('project' => 11), 'appIframe-project');
+ if($form->dom->linkedProduct->getText() != $project['otherProducts']['multiPicker']) return $this->failed('关联产品失败');
+ return $this->success('关联产品成功');
+ }
+ /**
+ * 取消关联产品。
+ * Unlink Product.
+ *
+ * @param array $project
+ * @access public
+ * @return void
+ */
+ public function unlinkProducts($project)
+ {
+ $form = $this->initForm('project', 'manageproducts', array('project' => 11), 'appIframe-project');
+ $form->dom->checkbox->click(); //取消勾选已关联产品
+ $form->wait(1);
+ $form->dom->saveBtn->click();
+
+ //跳转到项目概况页检查取消关联产品
+ $form = $this->initForm('project', 'view', array('project' => 11), 'appIframe-project');
+ if($form->dom->linkedProduct === false) return $this->success('取消关联产品成功');
+ return $this->failed('取消关联产品失败');
+ }
+}
diff --git a/module/project/test/lib/projectexport.ui.class.php b/module/project/test/lib/projectexport.ui.class.php
new file mode 100644
index 0000000000..172b3038f7
--- /dev/null
+++ b/module/project/test/lib/projectexport.ui.class.php
@@ -0,0 +1,27 @@
+initForm('project', 'browse');
+ $form->dom->exportBtn->click();
+ if(isset($project['filename'])) $form->dom->fileName->setValue($project['filename']);
+ if(isset($project['format'])) $form->dom->format->picker($project['format']);
+ if(isset($project['encoding'])) $form->dom->encoding->picker($project['encoding']);
+ if(isset($project['data'])) $form->dom->data->picker($project['data']);
+
+ $form->dom->exportBtnAlert->click();
+ $form->wait(2);
+ /*添加断言,是否导出成功*/
+ if($form->dom->exportBtnAlert) return $this->failed('项目导出失败');
+ return $this->success('项目导出成功');
+ }
+}
diff --git a/module/project/test/ui/browsetab.php b/module/project/test/ui/browsetab.php
new file mode 100644
index 0000000000..4b36746ab9
--- /dev/null
+++ b/module/project/test/ui/browsetab.php
@@ -0,0 +1,60 @@
+#!/usr/bin/env php
+id->range('1-8');
+$project->project->range('0');
+$project->model->range('scrum{3}, waterfall{3}, kanban{2}');
+$project->type->range('project');
+$project->attribute->range('[]');
+$project->auth->range('[]');
+$project->parent->range('0');
+$project->grade->range('1');
+$project->name->range('敏捷项目1, 敏捷项目2, 敏捷项目3, 瀑布项目4, 瀑布项目5, 瀑布项目6, 看板项目7, 看板项目8');
+$project->path->range('`,1,`, `,2,`, `,3,`, `,4,`, `,5,`, `,6,`, `,7,`, `,8,`');
+$project->begin->range('(-3w)-(-2w):1D')->type('timestamp')->format('YY/MM/DD');
+$project->end->range('(+5w)-(+6w):1D')->type('timestamp')->format('YY/MM/DD');
+$project->acl->range('open');
+$project->status->range('undone{3}, wait{2}, doing, suspended, closed');
+$project->gen(8);
+
+$tester = new browseTabTester();
+$tester->login();
+
+r($tester->checkBrowseTab('all', '8')) && p('message,status') && e('all标签下条数显示正确,SUCCESS'); // 检查all标签数量
+r($tester->checkBrowseTab('undone', '3')) && p('message,status') && e('undone标签下条数显示正确,SUCCESS'); // 检查undone标签数量
+r($tester->checkBrowseTab('wait', '2')) && p('message,status') && e('wait标签下条数显示正确,SUCCESS'); // 检查wait标签数量
+r($tester->checkBrowseTab('doing', '1')) && p('message,status') && e('doing标签下条数显示正确,SUCCESS'); // 检查doing标签数量
+r($tester->checkBrowseTab('suspended', '1')) && p('message,status') && e('suspended标签下条数显示正确,SUCCESS'); // 检查suspended标签数量
+r($tester->checkBrowseTab('closed', '1')) && p('message,status') && e('closed标签下条数显示正确,SUCCESS'); // 检查closed标签数量
+
+$tester->closeBrowser();
diff --git a/module/project/test/ui/createguide.php b/module/project/test/ui/createguide.php
new file mode 100755
index 0000000000..13eb524c0e
--- /dev/null
+++ b/module/project/test/ui/createguide.php
@@ -0,0 +1,30 @@
+#!/usr/bin/env php
+login();
+
+r($tester->createGuide('scrum')) && p('message') && e('scrum向导跳转正确'); // 检查scrum向导跳转
+r($tester->createGuide('waterfall')) && p('message') && e('waterfall向导跳转正确'); // 检查waterfall向导跳转
+r($tester->createGuide('kanban')) && p('message') && e('kanban向导跳转正确'); // 检查kanban向导跳转
+r($tester->createGuide('agileplus')) && p('message') && e('agileplus向导跳转正确'); // 检查agileplus向导跳转
+r($tester->createGuide('waterfallplus')) && p('message') && e('waterfallplus向导跳转正确'); // 检查waterfallplus向导跳转
+
+$tester->closeBrowser();
diff --git a/module/project/test/ui/group.php b/module/project/test/ui/group.php
new file mode 100755
index 0000000000..a5cb043173
--- /dev/null
+++ b/module/project/test/ui/group.php
@@ -0,0 +1,31 @@
+#!/usr/bin/env php
+loadYaml('project', false, 1)->gen(1);
+$tester = new groupTester();
+$tester->login();
+
+//设置项目分组数据
+$project = array(
+ array('groupname' => '', 'groupdesc' => ''),
+ array('groupname' => '项目分组1', 'groupdesc' => '一个分组描述哈哈哈222'),
+);
+
+r($tester->createGroup($project['0'])) && p('message') && e('项目创建分组提示信息正确'); // 创建项目分组提示信息检查
+r($tester->createGroup($project['1'])) && p('message') && e('项目分组创建成功'); // 创建项目分组成功
+
+$tester->closeBrowser();
diff --git a/module/project/test/ui/manageproducts.php b/module/project/test/ui/manageproducts.php
new file mode 100755
index 0000000000..9e04753efd
--- /dev/null
+++ b/module/project/test/ui/manageproducts.php
@@ -0,0 +1,31 @@
+#!/usr/bin/env php
+loadYaml('execution', false, 2)->gen(10);
+zendata('product')->loadYaml('product', false, 2)->gen(10);
+zendata('projectproduct')->loadYaml('projectproduct', false, 1)->gen(5);
+$tester = new manageProductsTester();
+$tester->login();
+
+$project = array(
+ array('otherProducts' => array('multiPicker' => '产品3')),
+);
+
+r($tester->linkNoProducts($project)) && p('message') && e('关联其他产品必填提示信息正确'); //校验选择产品不能为空
+r($tester->linkProducts($project['0'])) && p('message') && e('关联产品成功'); //关联产品
+r($tester->unlinkProducts($project)) && p('message') && e('取消关联产品成功'); //取消关联产品
+
+$tester->closeBrowser();
diff --git a/module/project/test/ui/page/browse.php b/module/project/test/ui/page/browse.php
index 6cf0104ebc..210635ae04 100644
--- a/module/project/test/ui/page/browse.php
+++ b/module/project/test/ui/page/browse.php
@@ -6,26 +6,49 @@ class browsePage extends page
parent::__construct($webdriver);
$xpath = array(
- 'settings' => "//*[@id='navbar']//a[@data-id='settings']/span",
- 'editBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div[1]/div/nav/a[2]/i",
- 'projectName' => "//*[@id='table-project-browse']/div[2]/div[1]/div/div[2]/div/a",
- 'scrumName' => "//*[@id='mainContent']/div[2]/div/div/div[2]/div/div/div[2]/div/a",
- 'moreBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div[1]/div/nav/button[1]/span",
- 'closeBtn' => "//*[@class='icon item-icon icon-off']",
- 'closeProject' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div[3]/div/div/form/div[3]/div/button",
- 'title' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div/div/div/span[1]",
- 'closed' => "//*[@id='more']/menu/menu/li[2]/a/div",
- 'activeBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div/div/nav/a[1]/i",
- 'activeProject' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div[3]/div/div/form/div[3]/div/button",
- 'startBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div/div/nav/a",
- 'startProject' => "//*[@class='modal-content']/div[3]/div/div/form/div[3]/div/button/span",
- 'suspendBtn' => "//*[@class='popover show fade dropdown in']/menu/menu/li/a",
- 'suspendProject' => "//*[@class='modal-content']/div[3]/div/div/form/div[2]/div/button",
- 'browseStatus' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div/div/span",
- 'selectBtn' => "//*[@id='table-project-browse']/div[2]/div[1]/div/div[1]",
- 'batchEditBtn' => "//*[@id='table-project-browse']/div[3]/nav[1]/nav/button/span",
- 'begin' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div[7]/div",
- 'end' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div[8]/div",
+ 'settings' => "//*[@id='navbar']//a[@data-id='settings']/span",
+ 'editBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div[1]/div/nav/a[2]/i",
+ 'projectName' => "//*[@id='table-project-browse']/div[2]/div[1]/div/div[2]/div/a",
+ 'scrumName' => "//*[@id='mainContent']/div[2]/div/div/div[2]/div/div/div[2]/div/a",
+ 'moreBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div[1]/div/nav/button[1]/span",
+ 'closeBtn' => "//*[@class='icon item-icon icon-off']",
+ 'closeProject' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div[3]/div/div/form/div[3]/div/button",
+ 'title' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div/div/div/span[1]",
+ 'closed' => "//*[@id='more']/menu/menu/li[2]/a/div",
+ 'activeBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div/div/nav/a[1]/i",
+ 'activeProject' => "//*[@class='modal modal-async load-indicator modal-trans show in']/div/div/div[3]/div/div/form/div[3]/div/button",
+ 'startBtn' => "//*[@id='table-project-browse']/div[2]/div[3]/div/div/div/nav/a",
+ 'startProject' => "//*[@class='modal-content']/div[3]/div/div/form/div[3]/div/button/span",
+ 'suspendBtn' => "//*[@class='popover show fade dropdown in']/menu/menu/li/a",
+ 'suspendProject' => "//*[@class='modal-content']/div[3]/div/div/form/div[2]/div/button",
+ 'browseStatus' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div/div/span",
+ 'selectBtn' => "//*[@id='table-project-browse']/div[2]/div[1]/div/div[1]",
+ 'batchEditBtn' => "//*[@id='table-project-browse']/div[3]/nav[1]/nav/button/span",
+ 'begin' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div[7]/div",
+ 'end' => "//*[@id='table-project-browse']/div[2]/div[2]/div/div[8]/div",
+ 'createProjectBtn' => "//*[@id='mainMenu']/div[2]/a[2]/span",
+ /*向导中项目管理方式类型*/
+ 'scrum' => "//*[@class='modal-content']/div[2]/div[2]/div[1]/div",
+ 'waterfall' => "//*[@class='modal-content']/div[2]/div[2]/div[2]/div",
+ 'kanban' => "//*[@class='modal-content']/div[2]/div[2]/div[3]/div",
+ 'agileplus' => "//*[@class='modal-content']/div[2]/div[2]/div[4]/div",
+ 'waterfallplus' => "//*[@class='modal-content']/div[2]/div[2]/div[5]/div",
+ /*导出项目*/
+ 'exportBtn' => "//*[@id='mainMenu']/div[2]/a/span",
+ 'fileName' => "//*[@class='modal-content']/div[3]/div/div/form/div/input",
+ 'format' => "//*[@class='modal-content']/div[3]/div/div/form/div[2]/div",
+ 'encoding' => "//*[@class='modal-content']/div[3]/div/div/form/div[3]/div/div",
+ 'data' => "//*[@class='modal-content']/div[3]/div/div/form/div[4]/div/div/div/span",
+ 'exportBtnAlert' => "//*[@class='modal-content']/div[3]/div/div/form/div[6]/div/button/span",
+ /*项目列表页标签*/
+ 'all' => "//*[@id='featureBar']/menu/li[1]/a/span[1]",
+ 'undone' => "//*[@id='featureBar']/menu/li[2]/a/span[1]",
+ 'wait' => "//*[@id='featureBar']/menu/li[3]/a/span[1]",
+ 'doing' => "//*[@id='featureBar']/menu/li[4]/a/span[1]",
+ 'moreTab' => "//*[@id='featureBar']/menu/li[5]/a/span[1]",
+ 'suspended' => "//*[@id='more']/menu/menu/li[1]/a/div/div",
+ 'closed' => "//*[@id='more']/menu/menu/li[2]/a/div/div",
+ 'num' => "//*[@id='table-project-browse']/div[3]/div[2]/strong"
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/project/test/ui/page/group.php b/module/project/test/ui/page/group.php
new file mode 100644
index 0000000000..4010b7b2ff
--- /dev/null
+++ b/module/project/test/ui/page/group.php
@@ -0,0 +1,16 @@
+ "//*[@class='modal-content']/div[3]/div/div/form/div/input",
+ 'groupDesc' => "//*[@class='modal-content']/div[3]/div/div/form/div[2]/textarea",
+ 'groupNameList' => "//*[@id='table-project-group']/div[2]/div[1]/div/div[2]/div",
+ 'groupDescList' => "//*[@id='table-project-group']/div[2]/div[2]/div/div/div",
+ 'createGroupBtn' => "//*[@id='mainMenu']/div[2]/a/span",
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/project/test/ui/page/manageproducts.php b/module/project/test/ui/page/manageproducts.php
new file mode 100644
index 0000000000..6b16c629d5
--- /dev/null
+++ b/module/project/test/ui/page/manageproducts.php
@@ -0,0 +1,15 @@
+ "//*[@id='manageProducts']/div[1]/div[2]/div[1]/a/p",
+ 'otherProducts' => "//*[@class='form-group-wrapper picker-box']/div/select",
+ 'checkbox' => "//*[@id='manageProducts']/div[1]/div[1]/div[2]/button[3]/div/label",
+ 'saveBtn' => "//*[@id='manageProducts']/div[2]/div/button/span",
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/project/test/ui/page/view.php b/module/project/test/ui/page/view.php
index 9049f87860..e8e544c64d 100644
--- a/module/project/test/ui/page/view.php
+++ b/module/project/test/ui/page/view.php
@@ -15,6 +15,7 @@ class viewPage extends page
'projectName' => "//*[@id='mainContent']/div[1]/div[1]/div[1]/div[2]/div[1]/span[2]",
'acl' => "//*[@id='mainContent']/div[1]/div[1]/div[1]/div[2]/div[1]/span[5]",
'end' => "//*[@id='mainContent']/div[1]/div[1]/div[2]/div/table[3]/tbody/tr/td/div/div[2]/span[2]",
+ 'linkedProduct' => "//*[@id='mainContent']/div[1]/div[1]/div[2]/div/table[1]/tbody/tr[3]/td[1]/div/div/a/span",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/project/test/ui/projectexport.php b/module/project/test/ui/projectexport.php
new file mode 100644
index 0000000000..d9ff3043dd
--- /dev/null
+++ b/module/project/test/ui/projectexport.php
@@ -0,0 +1,41 @@
+#!/usr/bin/env php
+loadYaml('project', false, 1)->gen(1);
+zendata('projectproduct')->loadYaml('projectproduct', false, 1)->gen(1);
+
+$tester = new projectExportTester();
+$tester->login();
+
+//设置项目导出数据
+$project = array(
+ array('filename' => ''),
+ array('filename' => '项目导出文件1', 'encoding' => 'GBK', 'data' => '选中记录'),
+ array('filename' => '项目导出文件2', 'format' => 'xml', 'data' => '全部记录'),
+);
+
+r($tester->projectExport($project['0'])) && p('message,status') && e('项目导出成功,SUCCESS'); // 按照默认设置导出项目
+r($tester->projectExport($project['1'])) && p('message,status') && e('项目导出成功,SUCCESS'); // 项目导出csv-GBK-选中记录
+r($tester->projectExport($project['2'])) && p('message,status') && e('项目导出成功,SUCCESS'); // 项目导出xml-全部记录
+
+$tester->closeBrowser();
diff --git a/module/project/test/ui/yaml/account.yaml b/module/project/test/ui/yaml/account.yaml
index 3e4e273907..0ea1093820 100644
--- a/module/project/test/ui/yaml/account.yaml
+++ b/module/project/test/ui/yaml/account.yaml
@@ -22,3 +22,5 @@ fields:
range: "e10adc3949ba59abbe56e057f20f883e"
- field: mobile
range: "``"
+ - field: visions
+ range: "`rnd,lite`"
diff --git a/module/project/test/ui/yaml/projectproduct.yaml b/module/project/test/ui/yaml/projectproduct.yaml
new file mode 100644
index 0000000000..8e9cee5fec
--- /dev/null
+++ b/module/project/test/ui/yaml/projectproduct.yaml
@@ -0,0 +1,13 @@
+title: projectproduct data
+author: Airong Hu
+version: 1.0.0
+
+fields:
+ - field: project
+ range: 11{2},60,61,100,101-700
+ - field: product
+ range: 1-2,3-30
+ - field: branch
+ range: 0
+ - field: plan
+ range: 0
diff --git a/module/project/ui/create.html.php b/module/project/ui/create.html.php
index 682fd6ef6d..42d33798d8 100644
--- a/module/project/ui/create.html.php
+++ b/module/project/ui/create.html.php
@@ -54,6 +54,7 @@ $handleLongTimeChange = jsCallback()->do(<<<'JS'
endPicker.render({disabled: isLongTime});
if(isLongTime) endPicker.$.setValue('');
$element.find('[name=days]').attr('disabled', isLongTime ? 'disabled' : null);
+ checkProjectInfo();
JS);
$toggleLongTime = jsCallback()->do(<<<'JS'
@@ -82,7 +83,7 @@ formGridPanel
divider(setClass('h-4 mr-4 ml-2 self-center'))
),
formHidden('storyType[]', 'story'),
- on::click('[name=name], [name=code], [data-name=begin] .pick *, [name=days], [data-name="parent"] .pick *', 'removeTips'),
+ on::click('[name=name], [name=code], [data-name=begin] .pick *, [name=days], [data-name="parent"] .pick *, [name=longTime]', 'removeTips'),
on::click('[type=submit]', 'removeAllTips'),
on::click('[name=multiple]', $toggleLongTime),
on::change('[name=hasProduct]', 'changeType'),
diff --git a/module/project/zen.php b/module/project/zen.php
index 146daf4995..ca3d2a8b58 100755
--- a/module/project/zen.php
+++ b/module/project/zen.php
@@ -1234,6 +1234,11 @@ class projectZen extends project
}
}
+ foreach($linkedProducts as $product)
+ {
+ if($product->deleted == '1') $product->name = $product->name . ' (' . $this->lang->product->deleted . ')';
+ }
+
$this->view->currentProducts = $currentProducts;
$this->view->otherProducts = $otherProducts;
$this->view->branchGroups = $branchGroups;
diff --git a/module/projectrelease/control.php b/module/projectrelease/control.php
index 8dbb3cbd86..c1e960370b 100644
--- a/module/projectrelease/control.php
+++ b/module/projectrelease/control.php
@@ -269,23 +269,13 @@ class projectrelease extends control
* 导出项目发布到 HTML。
* Export the stories of release to HTML.
*
+ * @param int $releaseID
* @access public
* @return void
*/
- public function export()
+ public function export(int $releaseID)
{
- if(!empty($_POST))
- {
- $type = $this->post->type;
-
- $html = '';
- if($type == 'story' || $type == 'all') $html .= $this->projectreleaseZen->generateStoryHtml();
- if($type == 'bug' || $type == 'all') $html .= $this->projectreleaseZen->generateBugHtml();
- if($type == 'leftbug' || $type == 'all') $html .= $this->projectreleaseZen->generateBugHtml('left');
- $html = "{$this->post->fileName}$html";
-
- return print($this->fetch('file', 'sendDownHeader', array('fileName' => $this->post->fileName, 'html', $html)));
- }
+ if(!empty($_POST)) return $this->fetch('release', 'export', "releaseID={$releaseID}");
$this->display('release', 'export');
}
diff --git a/module/projectrelease/test/lib/releaseexport.ui.class.php b/module/projectrelease/test/lib/releaseexport.ui.class.php
new file mode 100644
index 0000000000..762b8acbe8
--- /dev/null
+++ b/module/projectrelease/test/lib/releaseexport.ui.class.php
@@ -0,0 +1,44 @@
+initForm('projectrelease', 'view', array('releaseID' => 1), 'appIframe-project');
+ $form->dom->exportBtn->click();
+ if(isset($release['filename'])) $form->dom->fileName->setValue($release['filename']);
+ if(isset($release['exportdata'])) $form->dom->exportData->picker($release['exportdata']);
+
+ $form->dom->exportBtnAlert->click();
+ $form->wait(2);
+
+ if($form->dom->exportBtnAlert) return $this->failed('项目发布导出失败');
+ return $this->success('项目发布导出成功');
+ }
+
+ /**
+ * 项目发布导出时文件名为空时的必填校验检查。
+ * Check required tips of projectrelease export.
+ *
+ * @access public
+ * @return object
+ */
+ public function exportWithNoFilename()
+ {
+ $form = $this->initForm('projectrelease', 'view', array('releaseID' => 1), 'appIframe-project');
+ $form->dom->exportBtn->click();
+ $form->dom->exportBtnAlert->click();
+ $form->wait(2);
+
+ /*点击导出按钮后,检查必填校验*/
+ if($form->dom->alertModal('text') === '『文件名』不能为空。') return $this->success('项目发布导出必填提示信息正确');
+ return $this->failed('项目发布导出必填提示信息不正确');
+ }
+}
diff --git a/module/projectrelease/test/ui/page/view.php b/module/projectrelease/test/ui/page/view.php
index f378f9ade0..07bdcec6c4 100644
--- a/module/projectrelease/test/ui/page/view.php
+++ b/module/projectrelease/test/ui/page/view.php
@@ -18,14 +18,19 @@ class viewPage extends page
'unlinkFirBtn' => "//*[@id='finishedStoryDTable']/div[2]/div[3]/div/div/div/nav/a/i",
'allFinishedStoryBtn' => "//*[@id='finishedStoryDTable']/div[3]/div/div/label",
'batchUnlinkBtn' => "//*[@id='finishedStoryDTable']/div[3]/nav[1]/button[1]/span",
- 'resolvedBugTab' => "//*[@id='mainContent']/div[2]/div/div/div/div/ul/li[2]/a/span",
- 'linkBugBtn' => "//*[@id='mainContent']/div[2]/div/div/div/div[2]/div[2]/div/button/span",
- 'selectAllBug' => "//*[@id='unlinkBugList']/div[3]/div/div/label",
- 'linkBugBtnBottom' => "//*[@id='unlinkBugList']/div/nav/button/span",
- 'resolvedBugNum' => "//*[@id='resolvedBugDTable']/div[3]/div[2]/strong",
- 'unlinkFirBugBtn' => "//*[@id='resolvedBugDTable']/div[2]/div[3]/div/div/div/nav/a/i",
- 'allResolvedBugBtn' => "//*[@id='resolvedBugDTable']/div[3]/div/div/label",
- 'batchUnlinkBugBtn' => "//*[@id='resolvedBugDTable']/div[3]/nav[1]/button[1]/span",
+ /*发布关联Bug的元素*/
+ 'resolvedBugTab' => "//*[@id='mainContent']/div[2]/div/div/div/div/ul/li[2]/a/span",
+ 'linkBugBtn' => "//*[@id='mainContent']/div[2]/div/div/div/div[2]/div[2]/div/button/span",
+ 'selectAllBug' => "//*[@id='unlinkBugList']/div[3]/div/div/label",
+ 'linkBugBtnBottom' => "//*[@id='unlinkBugList']/div/nav/button/span",
+ 'resolvedBugNum' => "//*[@id='resolvedBugDTable']/div[3]/div[2]/strong",
+ 'unlinkFirBugBtn' => "//*[@id='resolvedBugDTable']/div[2]/div[3]/div/div/div/nav/a/i",
+ 'allResolvedBugBtn' => "//*[@id='resolvedBugDTable']/div[3]/div/div/label",
+ 'batchUnlinkBugBtn' => "//*[@id='resolvedBugDTable']/div[3]/nav[1]/button[1]/span",
+ /*导出HTML*/
+ 'exportBtn' => "//*[@id='mainContent']/div[2]/div/div/div/div[2]/div[2]/div/a/span",
+ 'exportData' => "//*[@class='panel-body']/form/div[2]/div/div/span",
+ 'exportBtnAlert' => "//*[@class='form-row']/div/button",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/projectrelease/test/ui/releaseexport.php b/module/projectrelease/test/ui/releaseexport.php
new file mode 100644
index 0000000000..00fb96b2a7
--- /dev/null
+++ b/module/projectrelease/test/ui/releaseexport.php
@@ -0,0 +1,42 @@
+#!/usr/bin/env php
+loadYaml('projectrelease', false, 1)->gen(1);
+zendata('project')->loadYaml('project', false, 1)->gen(1);
+zendata('projectproduct')->loadYaml('projectproduct', false, 1)->gen(1);
+
+$tester = new releaseExportTester();
+$tester->login();
+
+//设置导出发布数据
+$release = array(
+ array('filename' => ''),
+ array('filename' => '导出文件1'),
+ array('filename' => '导出文件2', 'exportdata' => '解决的Bug'),
+);
+
+r($tester->exportWithNoFilename($release['0'])) && p('message,status') && e('项目发布导出必填提示信息正确,SUCCESS'); // 项目发布导出时文件名必填项检查
+r($tester->releaseExport($release['1'])) && p('message,status') && e('项目发布导出成功,SUCCESS'); // 项目发布导出所有数据
+r($tester->releaseExport($release['2'])) && p('message,status') && e('项目发布导出成功,SUCCESS'); // 项目发布导出指定数据
+
+$tester->closeBrowser();
diff --git a/module/projectrelease/zen.php b/module/projectrelease/zen.php
index d2fc89309c..bd72906378 100644
--- a/module/projectrelease/zen.php
+++ b/module/projectrelease/zen.php
@@ -30,75 +30,4 @@ class projectreleaseZen extends projectrelease
$this->view->branch = $branch;
$this->view->project = $this->project->getByID($projectID);
}
-
- /**
- * 生成关联的需求的 html。
- * Generate story html.
- *
- * @access protected
- * @return void
- */
- protected function generateStoryHtml(): string
- {
- $this->loadModel('story');
-
- $html = "{$this->lang->release->stories}
";
-
- $fields = array('id' => $this->lang->story->id, 'title' => $this->lang->story->title);
-
- /* 生成表头。*/
- /* Generate thead.*/
- $html .= '';
- foreach($fields as $fieldLabel) $html .= "| $fieldLabel | \n";
- $html .= '
';
-
- $stories = $this->dbh->query($this->session->storyQueryCondition . " ORDER BY " . strtr($this->session->storyOrderBy, '_', ' '))->fetchAll();
- foreach($stories as $story)
- {
- $story->title = "id") . "' target='_blank'>$story->title";
-
- $html .= "\n";
- foreach($fields as $fieldName => $fieldLabel) $html .= '| ' . zget($story, $fieldName, '') . " | \n";
- $html .= "
\n";
- }
- $html .= '
';
-
- return $html;
- }
-
- /**
- * 生成 bug 的 html。
- * Generate bug html.
- *
- * @param string $type linked|left
- * @access protected
- * @return string
- */
- protected function generateBugHtml($type = 'linked'): string
- {
- $this->loadModel('bug');
-
- $html = '' . ($type == 'linked' ? $this->lang->release->bugs : $this->lang->release->generatedBugs) . '
';
-
- $fields = array('id' => $this->lang->bug->id, 'title' => $this->lang->bug->title);
-
- $html .= '';
- foreach($fields as $fieldLabel) $html .= "| $fieldLabel | \n";
- $html .= '
';
-
- $bugs = array();
- $queryConditionName = $type == 'linked' ? 'linkedBugQueryCondition' : 'leftBugsQueryCondition';
- if($this->session->$queryConditionName !== false) $bugs = $this->dao->select('id, title')->from(TABLE_BUG)->where($this->session->$queryConditionName)->beginIF($this->session->bugOrderBy !== false)->orderBy($this->session->bugOrderBy)->fi()->fetchAll('id');
- foreach($bugs as $bug)
- {
- $bug->title = "id") . "' target='_blank'>$bug->title";
-
- $html .= "\n";
- foreach($fields as $fieldName => $fieldLabel) $html .= "| " . zget($bug, $fieldName, '') . " | \n";
- $html .= "
\n";
- }
- $html .= '
';
-
- return $html;
- }
}
diff --git a/module/release/control.php b/module/release/control.php
index f99ba4871f..00eb894851 100755
--- a/module/release/control.php
+++ b/module/release/control.php
@@ -326,13 +326,12 @@ class release extends control
{
if(!empty($_POST))
{
- $release = $this->release->getByID($releaseID);
+ $release = $this->release->getByID($releaseID, true);
$type = $this->post->type;
$fileName = $this->post->fileName;
if(empty($fileName)) return $this->sendError(sprintf($this->lang->error->notempty, $this->lang->release->fileName));
- $html = '';
- $release = $this->release->getByID($releaseID, true);
+ $html = '';
if($type == 'story' || $type == 'all') $html .= $this->releaseZen->buildStoryDataForExport($release);
if($type == 'bug' || $type == 'all') $html .= $this->releaseZen->buildBugDataForExport($release, 'bug');
if($type == 'leftbug' || $type == 'all') $html .= $this->releaseZen->buildBugDataForExport($release, 'leftbug');
diff --git a/module/release/model.php b/module/release/model.php
index 9fd45e119e..94665f67e9 100755
--- a/module/release/model.php
+++ b/module/release/model.php
@@ -1106,10 +1106,11 @@ class releaseModel extends model
* @param string $bugIdList
* @param string $orderBy
* @param object $pager
+ * @param string $type linked|left
* @access public
* @return array
*/
- public function getBugList(string $bugIdList, string $orderBy = '', object $pager = null): array
+ public function getBugList(string $bugIdList, string $orderBy = '', object $pager = null, string $type = 'linked'): array
{
$bugs = array();
@@ -1122,7 +1123,7 @@ class releaseModel extends model
->page($pager)
->fetchAll();
- $this->loadModel('common')->saveQueryCondition($this->dao->get(), 'leftBugs');
+ $this->loadModel('common')->saveQueryCondition($this->dao->get(), $type == 'linked' ? 'linkedBug' : 'leftBugs');
}
return $bugs;
diff --git a/module/release/zen.php b/module/release/zen.php
index f584c587c0..76f9d74763 100644
--- a/module/release/zen.php
+++ b/module/release/zen.php
@@ -209,7 +209,7 @@ class releaseZen extends release
$bugs = $this->release->getBugList($release->bugs, $type == 'bug' ? $sort : '', $bugPager);
if($type == 'leftBug' && strpos($orderBy, 'severity_') !== false) $sort = str_replace('severity_', 'severityOrder_', $sort);
- $leftBugs = $this->release->getBugList($release->leftBugs, $type == 'leftBug' ? $sort : '', $leftBugPager);
+ $leftBugs = $this->release->getBugList($release->leftBugs, $type == 'leftBug' ? $sort : '', $leftBugPager, 'left');
$product = $this->loadModel('product')->getByID($release->product);
diff --git a/module/repo/js/diff.ui.js b/module/repo/js/diff.ui.js
index b3d220fbbd..e8dc4cd347 100644
--- a/module/repo/js/diff.ui.js
+++ b/module/repo/js/diff.ui.js
@@ -103,6 +103,9 @@ window.getDiffs = function(fileName)
'code': {'new': '', 'old': ''},
'line': {'new': [], 'old': []}
};
+
+ const newContent = [];
+ const oldContent = [];
$.each(diffs, function(i, diff)
{
if(diff.fileName == fileName)
@@ -116,17 +119,20 @@ window.getDiffs = function(fileName)
{
if(code.type == 'all' || code.type == 'new')
{
- result.code.new += htmlspecialchars_decode(code.line.substring(1)) + "\n";
+ newContent.push(htmlspecialchars_decode(code.line.substring(1)));
result.line.new.push(parseInt(code.newlc));
}
if(code.type == 'all' || code.type == 'old')
{
- result.code.old += htmlspecialchars_decode(code.line.substring(1)) + "\n";
+ oldContent.push(htmlspecialchars_decode(code.line.substring(1)));
result.line.old.push(parseInt(code.oldlc));
}
})
})
+
+ result.code.new = newContent.join('\n');
+ result.code.old = oldContent.join('\n');
return result;
}
});
diff --git a/module/repo/model.php b/module/repo/model.php
index 2f29627611..bda99d1a2f 100644
--- a/module/repo/model.php
+++ b/module/repo/model.php
@@ -213,7 +213,7 @@ class repoModel extends model
*/
public function createRepo(object $repo): int|false
{
- $check = $this->repoTao->checkName($repo);
+ $check = $this->checkName($repo->name);
if(!$check)
{
dao::$errors['name'] = $this->lang->repo->error->repoNameInvalid;
@@ -917,7 +917,7 @@ class repoModel extends model
$orderBy = $repo->SCM == 'Subversion' ? 'svnRevision desc' : 't1.time desc';
$branchID = (string)$this->cookie->repoBranch;
- $lastComment = $this->dao->select('t1.*,t1.revision*1 as svnRevision')->from(TABLE_REPOHISTORY)->alias('t1')
+ $lastComment = $this->dao->select('t1.*')->from(TABLE_REPOHISTORY)->alias('t1')
->leftJoin(TABLE_REPOBRANCH)->alias('t2')->on('t1.id=t2.revision')
->where('t1.repo')->eq($repoID)
->beginIF($repo->SCM != 'Subversion' && $branchID)->andWhere('t2.branch')->eq($branchID)->fi()
@@ -925,6 +925,8 @@ class repoModel extends model
->orderBy($orderBy)
->fetch();
if(empty($lastComment)) return false;
+
+ $lastComment->svnRevision = intval($lastComment->revision);
if(!$checkCount) return $lastComment;
$count = $this->dao->select('count(DISTINCT t1.id) as count')->from(TABLE_REPOHISTORY)->alias('t1')
@@ -3118,4 +3120,17 @@ class repoModel extends model
}
return $objectID;
}
+
+ /**
+ * Check repo name.
+ *
+ * @param string $name
+ * @access public
+ * @return bool
+ */
+ public function checkName(string $name)
+ {
+ $pattern = "/^[a-z_]{1}[a-z0-9_-]+$/i";
+ return preg_match($pattern, $name);
+ }
}
diff --git a/module/repo/tao.php b/module/repo/tao.php
index b229603f83..71085df8b9 100644
--- a/module/repo/tao.php
+++ b/module/repo/tao.php
@@ -67,19 +67,6 @@ class repoTao extends repoModel
return $this->session->$queryName;
}
- /**
- * Check repo name.
- *
- * @param object $repo
- * @access protected
- * @return bool
- */
- protected function checkName(object $repo)
- {
- $pattern = "/^[a-zA-Z_\-\.]+$/";
- return preg_match($pattern, $repo->name);
- }
-
/**
* 获取代码库分支的最后提交时间。
* Get the last commit time of repo branch.
diff --git a/module/repo/test/tao/checkname.php b/module/repo/test/model/checkname.php
similarity index 62%
rename from module/repo/test/tao/checkname.php
rename to module/repo/test/model/checkname.php
index fe6f91ff43..f4a63c1482 100755
--- a/module/repo/test/tao/checkname.php
+++ b/module/repo/test/model/checkname.php
@@ -19,9 +19,8 @@ zenData('pipeline')->gen(5);
$repoModel = $tester->loadModel('repo');
-$repo = new stdclass();
-$repo->name = 'abc&&';
-r($repoModel->checkName($repo)) && p() && e('0'); //使用不符合规则的名字
+$name = 'abc&&';
+r($repoModel->checkName($name)) && p() && e('0'); //使用不符合规则的名字
-$repo->name = 'unitTestProject17';
-r($repoModel->checkName($repo)) && p() && e('1'); //使用符合规则的名字
\ No newline at end of file
+$name = 'unitTestProject17';
+r($repoModel->checkName($name)) && p() && e('1'); //使用符合规则的名字
diff --git a/module/story/lang/de.php b/module/story/lang/de.php
index 07ff8eed7a..d20703b18b 100644
--- a/module/story/lang/de.php
+++ b/module/story/lang/de.php
@@ -220,6 +220,7 @@ $lang->story->completeRate = 'Completion Rate';
$lang->story->reviewed = 'Reviewed';
$lang->story->toBeReviewed = 'To Be Reviewed';
$lang->story->linkMR = 'Related MRs';
+$lang->story->linkPR = 'Related PRs';
$lang->story->linkCommit = 'Related Commits';
$lang->story->URS = 'User requirements';
$lang->story->estimateUnit = "(Unit: {$lang->story->hour})";
diff --git a/module/story/lang/en.php b/module/story/lang/en.php
index f37c01b86b..68f65f0ae1 100644
--- a/module/story/lang/en.php
+++ b/module/story/lang/en.php
@@ -220,6 +220,7 @@ $lang->story->completeRate = 'Completion Rate';
$lang->story->reviewed = 'Reviewed';
$lang->story->toBeReviewed = 'To Be Reviewed';
$lang->story->linkMR = 'Related MRs';
+$lang->story->linkPR = 'Related PRs';
$lang->story->linkCommit = 'Related Commits';
$lang->story->URS = 'User requirements';
$lang->story->estimateUnit = "(Unit: {$lang->story->hour})";
diff --git a/module/story/lang/fr.php b/module/story/lang/fr.php
index 340b443558..16d2f164ce 100644
--- a/module/story/lang/fr.php
+++ b/module/story/lang/fr.php
@@ -220,6 +220,7 @@ $lang->story->completeRate = 'Completion Rate';
$lang->story->reviewed = 'Reviewed';
$lang->story->toBeReviewed = 'To Be Reviewed';
$lang->story->linkMR = 'Related MRs';
+$lang->story->linkPR = 'Related PRs';
$lang->story->linkCommit = 'Related Commits';
$lang->story->URS = 'User requirements';
$lang->story->estimateUnit = "(Unit: {$lang->story->hour})";
diff --git a/module/story/lang/zh-cn.php b/module/story/lang/zh-cn.php
index 5256b69612..e227efb2e8 100644
--- a/module/story/lang/zh-cn.php
+++ b/module/story/lang/zh-cn.php
@@ -220,6 +220,7 @@ $lang->story->completeRate = '完成率';
$lang->story->reviewed = '已评审';
$lang->story->toBeReviewed = '待评审';
$lang->story->linkMR = '相关合并请求';
+$lang->story->linkPR = '相关推送请求';
$lang->story->linkCommit = '相关代码版本';
$lang->story->URS = '用户需求';
$lang->story->estimateUnit = "(单位:{$lang->story->hour})";
diff --git a/module/story/model.php b/module/story/model.php
index 3e327af477..25ccedf7e5 100644
--- a/module/story/model.php
+++ b/module/story/model.php
@@ -3690,7 +3690,7 @@ class storyModel extends model
}
}
- if(strtolower($actionType) == 'changed' or strtolower($actionType) == 'opened')
+ if(in_array(strtolower($actionType), array('changed', 'opened', 'submitreview')))
{
$reviewerList = $this->getReviewerPairs($story->id, $story->version);
unset($reviewerList[$story->assignedTo]);
@@ -5471,8 +5471,8 @@ class storyModel extends model
{
return $this->dao->select('t1.revision,t3.id AS id,t3.title AS title')
->from(TABLE_REPOHISTORY)->alias('t1')
- ->leftJoin(TABLE_RELATION)->alias('t2')->on('t2.relation="completedin" AND t2.BType="commit" AND t2.BID=t1.id')
- ->leftJoin(TABLE_STORY)->alias('t3')->on('t2.AType="story" AND t2.AID=t3.id')
+ ->leftJoin(TABLE_RELATION)->alias('t2')->on("t2.relation='completedin' AND t2.BType='commit' AND t2.BID=t1.id")
+ ->leftJoin(TABLE_STORY)->alias('t3')->on("t2.AType='story' AND t2.AID=t3.id")
->where('t1.revision')->in($revisions)
->andWhere('t1.repo')->eq($repoID)
->andWhere('t3.id')->ne('')
diff --git a/module/story/test/lib/createstory.ui.class.php b/module/story/test/lib/createstory.ui.class.php
index 13e06bd06b..54c2fa0aad 100755
--- a/module/story/test/lib/createstory.ui.class.php
+++ b/module/story/test/lib/createstory.ui.class.php
@@ -15,13 +15,13 @@ class createStoryTester extends tester
/**
* Create a default story.
*
- * @param string $type string $storyName
+ * @param string $type
+ * @param string $storyName
* @access public
* @return object
*/
public function createDefault($storyType, $storyName)
{
- /* 提交表单 */
$createStoryParam = array(
'product' => '1',
'branch' => 'all',
@@ -41,8 +41,8 @@ class createStoryTester extends tester
'param' => '0',
'storyType' => $storyType
);
- $form = $this->initForm('product', 'browse', $browseStoryParam, 'appIframe-product');
- $form = $this->initForm($storyType, 'create', $createStoryParam, 'appIframe-product');
+ $form = $this->initForm('product', 'browse', $browseStoryParam, 'appIframe-product'); //由于创建需求后会跳转到记录了session的页面,所以先进入一次对应需求的列表页面
+ $form = $this->initForm($storyType, 'create', $createStoryParam, 'appIframe-product'); //再进入创建需求页面
$form->dom->title->setValue($storyName);
$form->dom->assignedTo->picker('admin');
#$form->dom->reviewer->multiPicker(array('admin'));
@@ -84,4 +84,85 @@ class createStoryTester extends tester
return $this->success('创建'.$storyName.'成功');
}
+
+ /**
+ * Batchchreate a default storis.
+ *
+ * @param string $type
+ * @param string $storyName
+ * @access public
+ * @return object
+ */
+ public function batchCreateDefault($storyType, $storyName)
+ {
+ $browseStoryParam = array(
+ 'productID' => '1',
+ 'branch' => '',
+ 'browseType' => 'unclosed',
+ 'param' => '0',
+ 'storyType' => $storyType
+ );
+ $createStoryParam = array(
+ 'productID' => '1',
+ 'branch' => 'all',
+ 'moduleID' => '0',
+ 'storyID' => '0',
+ 'project' => '0',
+ 'plan' => '0',
+ 'storyType' => $storyType
+ );
+ /* 跳转到列表记录session,然后再次进入批量创建需求页面。*/
+ $form = $this->initForm('product', 'browse', $browseStoryParam, 'appIframe-product');
+ $form = $this->initForm($storyType, 'batchCreate', $createStoryParam, 'appIframe-product');
+ $form->dom->name->setValue($storyName);
+ if($storyName == '批量创建业务需求')
+ {
+ $form->dom->epicSave->click();
+ }
+ elseif($storyName == '批量创建用户需求')
+ {
+ $form->dom->requirementSave->click();
+ }
+ else
+ {
+ $form->dom->storySave->click();
+ }
+ $form->dom->btn($this->lang->save)->click();
+ $form->wait(1);
+
+ if($this->response('method') != 'browse')
+ {
+ if($form->dom->alertModal('text') == '已有相同标题的需求或标题为空,请检查输入。') return $this->success('批量创建需求表单页面提示正确');
+ return $this->failed('批量创建需求表单页面提示信息不正确');
+ }
+
+ /* 跳转到需求列表页面搜索创建需求并进入该需求详情页。 */
+ if($storyName != '批量创建研发需求')
+ {
+ $ext = array(
+ 'productID' => '1',
+ 'branch' => '',
+ 'brwoseType' => 'unclosed',
+ 'param' => '0',
+ 'storyType' => $storyType
+ );
+ $browsePage = $this->loadPage('product', 'browse', $ext);
+ }
+ else
+ {
+ $browsePage = $this->loadPage('product', 'browse');
+ }
+ $browsePage->dom->search($searchList = array("需求名称,包含,$storyName"));
+ $form->wait(1);
+ $browsePage->dom->browseStoryName->click();
+ $form->wait(1);
+
+ $viewPage = $this->loadPage('story', 'view');
+ if($viewPage->dom->storyName->getText() != $storyName) return $this->failed('需求名称不正确');
+ if($viewPage->dom->status->getText() != '激活') return $this->failed('需求状态不正确');
+ $viewPage->dom->btn($this->lang->story->legendLifeTime)->click();
+ if(strpos($viewPage->dom->openedBy->getText() , 'admin') === false) return $this->failed('创建人不正确');
+
+ return $this->success('批量创建'.$storyName.'成功');
+ }
}
diff --git a/module/story/test/lib/editstory.ui.class.php b/module/story/test/lib/editstory.ui.class.php
index 20b6068b64..fbdd0d86c7 100755
--- a/module/story/test/lib/editstory.ui.class.php
+++ b/module/story/test/lib/editstory.ui.class.php
@@ -14,7 +14,6 @@ class editStoryTester extends tester
{
/**
* Edit a story.
- *
* @param string $storyFrom
* @access public
* @return object
@@ -35,9 +34,32 @@ class editStoryTester extends tester
$browsePage = $this->loadPage('story', 'view', '1');
- $viewPafe = $this->loadPage('story', 'view');
- if($viewPafe->dom->storyFrom->getText() != '客户') return $this->failed('需求来源不正确');
+ $viewPage = $this->loadPage('story', 'view');
+ if($viewPage->dom->storyFrom->getText() != '客户') return $this->failed('需求来源不正确');
return $this->success('编辑研发需求成功');
}
+
+ /**
+ * batch a story.
+ * @param string $storyFrom
+ * @access public
+ * @return object
+ */
+ public function batchEditStory($storyFrom)
+ {
+ $browsePage = $this->initForm('product', 'browse', '1');
+ $browsePage->dom->firstSelect->click();
+ $browsePage->dom->batchEdit->click();
+ sleep(1);
+ $batchEdit = $this->loadPage('story', 'batchEdit');
+ $batchEdit->dom->batchSource->picker($storyFrom);
+ $batchEdit->dom->batchEditSave->click();
+ $batchEdit->wait(1);
+
+ $viewPage = $this->initForm('story', 'view', array('storyID' => '1'), 'appIframe-product');
+ if($viewPage->dom->storyFrom->getText() != '客户') return $this->failed('需求来源不正确');
+
+ return $this->success('批量编辑研发需求成功');
+ }
}
diff --git a/module/story/test/ui/creatstory.php b/module/story/test/ui/creatstory.php
index fbc257e88e..7b06747e36 100644
--- a/module/story/test/ui/creatstory.php
+++ b/module/story/test/ui/creatstory.php
@@ -8,7 +8,7 @@ timeout=0
cid=80
- 缺少需求名称,创建失败
- - 测试结果 @创建产品表单页提示信息正确
+ - 测试结果 @创建需求表单页提示信息正确
- 最终测试状态 @SUCCESS
- 使用默认选项创建研发需求 最终测试状态 @SUCCESS
- 使用默认选项创建用户需求 最终测试状态 @SUCCESS
@@ -18,10 +18,21 @@ cid=80
- 属性method @view
- 创建需求成功 最终测试状态 @SUCCESS
+- 批量创建需求缺少需求名称,创建失败
+ - 测试结果 @批量创建需求表单页提示信息正确
+ - 最终测试状态 @SUCCESS
+- 使用默认选项批量创建研发需求 最终测试状态 @SUCCESS
+- 使用默认选项批量创建用户需求 最终测试状态 @SUCCESS
+- 使用默认选项批量创建业务需求 最终测试状态 @SUCCESS
+- 批量创建需求成功后检查创建的需求信息是否正确
+ - 属性module @story
+ - 属性method @view
+- 批量创建需求成功 最终测试状态 @SUCCESS
*/
chdir(__DIR__);
include '../lib/createstory.ui.class.php';
include 'page/create.php';
+include 'page/batchcreate.php';
$product = zenData('product');
$product->id->range('1');
@@ -60,15 +71,31 @@ $storyspec->version->range('1');
$storyspec->title->range('激活研发需求,激活用户需求,激活业务需求');
$storyspec->gen(3);
+$action = zenData('action');
+$action->id->range('1-4');
+$action->objectType->range('product,story,story,story');
+$action->objectID->range('1,1,2,3');
+$action->product->range('`,1,`');
+$action->project->range('0');
+$action->execution->range('0');
+$action->actor->range('admin');
+$action->action->range('opened');
+$action->read->range('0');
+$action->vision->range('rnd');
+$action->gen(4);
+
$tester = new createStoryTester();
$tester->login();
$storys = array();
-$storys['null'] = '';
-$storys['story'] = '研发需求';
-$storys['requirement'] = '用户需求';
-$storys['epic'] = '业务需求';
-$storys['childStory'] = '子需求';
+$storys['null'] = '';
+$storys['story'] = '研发需求';
+$storys['requirement'] = '用户需求';
+$storys['epic'] = '业务需求';
+$storys['childStory'] = '子需求';
+$storys['batchstory'] = '批量创建研发需求';
+$storys['batchrequirement'] = '批量创建用户需求';
+$storys['batchepic'] = '批量创建业务需求';
$storyType = array();
$storyType['epic'] = 'epic';
@@ -80,4 +107,9 @@ r($tester->createDefault($storyType['story'], $storys['story'])) &&
r($tester->createDefault($storyType['requirement'], $storys['requirement'])) && p('message,status') && e('创建用户需求成功,SUCCESS'); // 使用默认选项创建用户需求,搜索后详情页信息对应
r($tester->createDefault($storyType['epic'], $storys['epic'])) && p('message,status') && e('创建业务需求成功,SUCCESS'); // 使用默认选项创建业务需求,搜索后详情页信息对应
+r($tester->batchCreateDefault($storyType['story'], $storys['null'])) && p('message,status') && e('批量创建需求页面名称为空提示正确,SUCCESS'); // 缺少需求名称,创建失败
+r($tester->batchcreateDefault($storyType['story'], $storys['batchstory'])) && p('message,status') && e('批量创建研发需求成功,SUCCESS'); // 使用默认选项批量创建需求,搜索后详情页信息对应
+r($tester->batchcreateDefault($storyType['requirement'], $storys['batchrequirement'])) && p('message,status') && e('批量创建用户需求成功,SUCCESS'); // 使用默认选项批量创建用户需求,搜索后详情页信息对应
+r($tester->batchcreateDefault($storyType['epic'], $storys['batchepic'])) && p('message,status') && e('批量创建业务需求成功,SUCCESS'); // 使用默认选项批量创建业务需求,搜索后详情页信息对应
+
$tester->closeBrowser();
diff --git a/module/story/test/ui/editstory.php b/module/story/test/ui/editstory.php
index 225df06ba8..b14f8a3937 100644
--- a/module/story/test/ui/editstory.php
+++ b/module/story/test/ui/editstory.php
@@ -13,6 +13,8 @@ cid=80
- 编辑研发需求
- 成功 最终测试状态 @SUCCESS
+- 批量编辑研发需求
+ - 成功 最终测试状态 @SUCCESS
*/
chdir(__DIR__);
include '../lib/editstory.ui.class.php';
@@ -35,6 +37,8 @@ $story->path->range('`,1,`, `,2,`, `,3,`');
$story->grade->range('1');
$story->product->range('1');
$story->module->range('0');
+$story->plan->range('0');
+$story->source->range('[]');
$story->title->range('激活研发需求,激活用户需求,激活业务需求');
$story->type->range('story,requirement,epic');
$story->stage->range('wait');
@@ -54,6 +58,19 @@ $storyspec->version->range('1');
$storyspec->title->range('激活研发需求,激活用户需求,激活业务需求');
$storyspec->gen(3);
+$action = zenData('action');
+$action->id->range('1-4');
+$action->objectType->range('product,story,story,story');
+$action->objectID->range('1,1,2,3');
+$action->product->range('`,1,`');
+$action->project->range('0');
+$action->execution->range('0');
+$action->actor->range('admin');
+$action->action->range('opened');
+$action->read->range('0');
+$action->vision->range('rnd');
+$action->gen(4);
+
$tester = new editStoryTester();
$tester->login();
@@ -62,4 +79,5 @@ $storyFrom = '客户';
r($tester->editStory($storyFrom)) && p('module,method') && e('story,view'); // 编辑需求后跳转页面检查
r($tester->editStory($storyFrom)) && p('message,status') && e('编辑需求成功,SUCCESS'); // 编辑需求成功
+r($tester->batchEditStory($storyFrom)) && p('message,status') && e('批量编辑研发需求成功,SUCCESS'); // 批量编辑需求成功
$tester->closeBrowser();
diff --git a/module/story/test/ui/page/batchcreate.php b/module/story/test/ui/page/batchcreate.php
new file mode 100755
index 0000000000..85ba96066a
--- /dev/null
+++ b/module/story/test/ui/page/batchcreate.php
@@ -0,0 +1,19 @@
+ "/html/body/div[1]/div/div/div/div[2]/form/div[1]/table/tbody/tr[1]/td[8]/div/input",
+ 'reviewer' => "/html/body/div[1]/div/div/div/div[2]/form/div[1]/table/tbody/tr[1]/td[16]/div/div",
+ 'storySave' => "//*[@id='zin_story_batchcreate_formBatch']/div[2]/button[1]",
+ 'requirementSave' => "//*[@id='zin_requirement_batchcreate_formBatch']/div[2]/button[1]",
+ 'epicSave' => "//*[@id='zin_epic_batchcreate_formBatch']/div[2]/button[1]"
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+
+
+}
diff --git a/module/story/test/ui/page/batchedit.php b/module/story/test/ui/page/batchedit.php
new file mode 100644
index 0000000000..56eae1a634
--- /dev/null
+++ b/module/story/test/ui/page/batchedit.php
@@ -0,0 +1,13 @@
+ "/html/body/div[1]/div/div/div/div[2]/form/div[1]/table/tbody/tr/td[10]/div/div",
+ 'batchEditSave' => "//*[@id='zin_story_batchedit_formBatch']/div[2]/button[1]"
+ );
+ $this->dom->xpath = array_merge($this->dom->xpath, $xpath);
+ }
+}
diff --git a/module/story/test/ui/page/view.php b/module/story/test/ui/page/view.php
index a5d63a9195..4bb9e968f8 100755
--- a/module/story/test/ui/page/view.php
+++ b/module/story/test/ui/page/view.php
@@ -6,16 +6,15 @@ class viewPage extends page
parent::__construct($webdriver);
$xpath = array(
- 'storyName' => "//*[@id='mainContent']/div/div[1]/div[1]/span[2]",
- 'status' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[1]/div/div[6]/div[2]/span",
- 'storyFrom' => "//*[@id='sourceBox']",
- 'openedBy' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[1]/div[2]",
- 'closeReason' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[6]/div[2]",
- 'reviewer' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[3]/div[2]/div/span",
- 'assignToONE' => "/html/body/div/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[2]/div[2]",
- 'activate' => "//*[@type='submit']",
- 'assignToBtn' => "//*[@type='submit']",
- 'reviewer' => "/html/body/div[1]/div/div/div[1]/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[3]/div[2]/div/span"
+ 'storyName' => "//*[@id='mainContent']/div/div[1]/div[1]/span[2]",
+ 'storyFrom' => "//*[@id='sourceBox']",
+ 'status' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[1]/div/div[6]/div[2]/span",
+ 'openedBy' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[1]/div[2]",
+ 'assignToONE' => "/html/body/div/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[2]/div[2]",
+ 'reviewer' => "/html/body/div[1]/div/div/div[1]/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[3]/div[2]/div/span"
+ 'closeReason' => "/html/body/div[1]/div/div/div/div[2]/div[2]/div[1]/div[2]/div[2]/div/div[6]/div[2]",
+ 'activate' => "//*[@type='submit']",
+ 'assignToBtn' => "//*[@type='submit']",
);
$this->dom->xpath = array_merge($this->dom->xpath, $xpath);
}
diff --git a/module/task/config/form.php b/module/task/config/form.php
index 73c8f4f1b1..00264029c1 100644
--- a/module/task/config/form.php
+++ b/module/task/config/form.php
@@ -125,6 +125,7 @@ $config->task->form->batchcreate['deadline'] = array('type' => 'date',
$config->task->form->batchcreate['desc'] = array('type' => 'string', 'required' => false, 'default' => '');
$config->task->form->batchcreate['pri'] = array('type' => 'int', 'required' => false, 'default' => 0);
$config->task->form->batchcreate['lane'] = array('type' => 'int', 'required' => false, 'default' => 0);
+$config->task->form->batchcreate['column'] = array('type' => 'int', 'required' => false, 'default' => 0);
$config->task->form->batchcreate['openedBy'] = array('type' => 'string', 'required' => false, 'default' => $account);
$config->task->form->batchcreate['openedDate'] = array('type' => 'datetime', 'required' => false, 'default' => $now);
$config->task->form->batchcreate['vision'] = array('type' => 'string', 'required' => false, 'default' => $config->vision);
diff --git a/module/task/lang/de.php b/module/task/lang/de.php
index c5155b0eb8..4d50fc34be 100644
--- a/module/task/lang/de.php
+++ b/module/task/lang/de.php
@@ -202,6 +202,7 @@ $lang->task->noClosed = 'Niht geschlossen';
$lang->task->yesterdayFinished = 'Gestern abgeschlossen';
$lang->task->allTasks = 'Alle Aufgaben';
$lang->task->linkMR = 'Related MRs';
+$lang->task->linkPR = 'Related PRs';
$lang->task->linkCommit = 'Related Commits';
$lang->task->statusList[''] = '';
diff --git a/module/task/lang/en.php b/module/task/lang/en.php
index f2e92a305f..1c550579c3 100755
--- a/module/task/lang/en.php
+++ b/module/task/lang/en.php
@@ -202,6 +202,7 @@ $lang->task->noClosed = 'Unclosed';
$lang->task->yesterdayFinished = 'Task Finished Yesterday';
$lang->task->allTasks = 'Task';
$lang->task->linkMR = 'Related MRs';
+$lang->task->linkPR = 'Related PRs';
$lang->task->linkCommit = 'Related Commits';
$lang->task->statusList[''] = '';
diff --git a/module/task/lang/fr.php b/module/task/lang/fr.php
index 09bd4fadc2..ea98252a84 100644
--- a/module/task/lang/fr.php
+++ b/module/task/lang/fr.php
@@ -202,6 +202,7 @@ $lang->task->noClosed = 'Non Fermées';
$lang->task->yesterdayFinished = 'Tâche Terminée Hier';
$lang->task->allTasks = 'Tâche';
$lang->task->linkMR = 'Related MRs';
+$lang->task->linkPR = 'Related PRs';
$lang->task->linkCommit = 'Related Commits';
$lang->task->statusList[''] = '';
diff --git a/module/task/lang/zh-cn.php b/module/task/lang/zh-cn.php
index 0cd2875a70..542ab9a960 100755
--- a/module/task/lang/zh-cn.php
+++ b/module/task/lang/zh-cn.php
@@ -202,6 +202,7 @@ $lang->task->noClosed = '未关闭';
$lang->task->yesterdayFinished = '昨日完成任务数';
$lang->task->allTasks = '总任务';
$lang->task->linkMR = '相关合并请求';
+$lang->task->linkPR = '相关推送请求';
$lang->task->linkCommit = '相关代码版本';
$lang->task->statusList[''] = '';
diff --git a/module/task/model.php b/module/task/model.php
index 719af38cbc..57eaf5e42e 100755
--- a/module/task/model.php
+++ b/module/task/model.php
@@ -501,8 +501,9 @@ class taskModel extends model
{
/* Get the lane and column of the current task. */
$laneID = $task->lane;
- $columnID = isset($output['columnID']) ? $output['columnID'] : 0;
+ $columnID = $task->column;
unset($task->lane);
+ unset($task->column);
/* Create a task. */
$taskID = $this->create($task);
@@ -3335,8 +3336,8 @@ class taskModel extends model
{
return $this->dao->select('t1.revision,t3.id AS id,t3.name AS name')
->from(TABLE_REPOHISTORY)->alias('t1')
- ->leftJoin(TABLE_RELATION)->alias('t2')->on('t2.relation="completedin" AND t2.BType="commit" AND t2.BID=t1.id')
- ->leftJoin(TABLE_TASK)->alias('t3')->on('t2.AType="task" AND t2.AID=t3.id')
+ ->leftJoin(TABLE_RELATION)->alias('t2')->on("t2.relation='completedin' AND t2.BType='commit' AND t2.BID=t1.id")
+ ->leftJoin(TABLE_TASK)->alias('t3')->on("t2.AType='task' AND t2.AID=t3.id")
->where('t1.revision')->in($revisions)
->andWhere('t1.repo')->eq($repoID)
->andWhere('t3.id')->ne('')
diff --git a/module/task/ui/edit.html.php b/module/task/ui/edit.html.php
index 5ccbe3bf20..f86401c948 100644
--- a/module/task/ui/edit.html.php
+++ b/module/task/ui/edit.html.php
@@ -227,7 +227,7 @@ detailBody
)
)
),
- $task->parent >= 0 && empty($task->team) ? item
+ $task->parent >= 0 && empty($task->team) && $config->vision != 'lite' ? item
(
set::name($lang->task->parent),
picker
diff --git a/module/task/ui/recordworkhour.html.php b/module/task/ui/recordworkhour.html.php
index c73c73fad3..3102ba8253 100644
--- a/module/task/ui/recordworkhour.html.php
+++ b/module/task/ui/recordworkhour.html.php
@@ -72,7 +72,7 @@ if($efforts)
h::td($effort->id),
h::td($effort->date),
h::td(zget($users, $effort->account)),
- h::td(html($effort->work)),
+ h::td(html($effort->work), setClass('break-all')),
h::td("{$effort->consumed} {$lang->task->suffixHour}"),
h::td("{$effort->left} {$lang->task->suffixHour}"),
h::td
diff --git a/module/task/zen.php b/module/task/zen.php
index 59ac2947bb..7feda78dbb 100644
--- a/module/task/zen.php
+++ b/module/task/zen.php
@@ -554,7 +554,8 @@ class taskZen extends task
$task->execution = $execution->id;
$task->left = $task->estimate;
$task->parent = $taskID;
- $task->lane = empty($task->lane) && !empty($output['laneID']) ? (int)$output['laneID'] : $task->lane;
+ $task->lane = !empty($task->lane) ? $task->lane : zget($output, 'laneID', 0);
+ $task->column = !empty($task->column) ? $task->column : zget($output, 'columnID', 0);
$task->storyVersion = $task->story ? $this->story->getVersion($task->story) : 1;
}
diff --git a/module/testcase/control.php b/module/testcase/control.php
index f86bded256..070acc497b 100644
--- a/module/testcase/control.php
+++ b/module/testcase/control.php
@@ -888,6 +888,7 @@ class testcase extends control
->set('fromCaseVersion')->eq($version)
->set('precondition')->eq($libCase->precondition)
->set('title')->eq($libCase->title)
+ ->set('keywords')->eq($libCase->keywords)
->where('id')->eq($caseID)
->exec();
diff --git a/module/testcase/test/lib/testcase.ui.class.php b/module/testcase/test/lib/testcase.ui.class.php
index f4c6eba23d..fedd8bdaeb 100644
--- a/module/testcase/test/lib/testcase.ui.class.php
+++ b/module/testcase/test/lib/testcase.ui.class.php
@@ -1,5 +1,6 @@
-#!/usr/bin/env php
dom->{"steps[$parentGroup]"}->scrollToElement();
$form->dom->{"steps[$parentGroup]"}->setValue($parentSteps);
$form->dom->{"expects[$parentGroup]"}->setValue($parentExpects);
}
else
{
$group = 0;
+ $form->dom->{"steps[$parentGroup]"}->setValue($parentSteps);
$subButton = "//textarea[@name = 'steps[$parentGroup]']/../..//button[@data-action='sub']/i";
- $this->page->scrollToElement($subButton);
- $this->page->click($subButton);
+ $subButtonXpath = $this->page->webdriver->driver->findElement(WebDriverBy::xpath($subButton));
+ $this->page->webdriver->driver->executeScript("arguments[0].click();", [$subButtonXpath]);
foreach($parentExpects as $steps => $expects)
{
$group++;
+ $this->webdriver->wait(1);
+ $sibButton = "//textarea[@name = 'steps[$parentGroup.$group]']/../..//button[@data-action='sib']/i";
+ $sibButtonXpath = $this->page->webdriver->driver->findElement(WebDriverBy::xpath($sibButton));
if(!is_array($expects))
{
- $form->dom->{"steps[$parentGroup.$group]"}->scrollToElement();
$form->dom->{"steps[$parentGroup.$group]"}->setValue($steps);
$form->dom->{"expects[$parentGroup.$group]"}->setValue($expects);
+ $this->page->webdriver->driver->executeScript("arguments[0].click();", [$sibButtonXpath]);
+ }
+ else
+ {
+ $sonGroup = 0;
+ $form->dom->{"steps[$parentGroup.$group]"}->setValue($steps);
+ $sonSubButton = "//textarea[@name = 'steps[$parentGroup.$group]']/../..//button[@data-action='sub']/i";
+ $sonSubButtonXpath = $this->page->webdriver->driver->findElement(WebDriverBy::xpath($sonSubButton));
+ $this->page->webdriver->driver->executeScript("arguments[0].click();", [$sonSubButtonXpath]);
}
}
}
diff --git a/module/testcase/zen.php b/module/testcase/zen.php
index 8c9ad0f1ef..8fdd4667c6 100755
--- a/module/testcase/zen.php
+++ b/module/testcase/zen.php
@@ -1303,6 +1303,9 @@ class testcaseZen extends testcase
$case = $this->testcase->appendCaseFails($case, $from, $taskID);
$case = $this->processStepsForMindMap($case);
+ $sceneOptionMenu = $this->testcase->getSceneMenu($case->product, $case->module);
+ if(!isset($sceneOptionMenu[$case->scene])) $sceneOptionMenu += $this->testcase->getScenesName((array)$case->scene);
+
$this->view->from = $from;
$this->view->taskID = $taskID;
$this->view->runID = $from == 'testcase' ? 0 : $run->id;
@@ -1313,6 +1316,7 @@ class testcaseZen extends testcase
$this->view->preAndNext = !isOnlybody() ? $this->loadModel('common')->getPreAndNextObject('testcase', $case->id) : '';
$this->view->users = $this->user->getPairs('noletter');
$this->view->actions = $this->loadModel('action')->getList('case', $case->id);
+ $this->view->scenes = $sceneOptionMenu;
}
/**
diff --git a/module/testreport/js/common.ui.js b/module/testreport/js/common.ui.js
index ed23f3065a..5ea9268b8e 100644
--- a/module/testreport/js/common.ui.js
+++ b/module/testreport/js/common.ui.js
@@ -1,12 +1,3 @@
-$().ready(function()
-{
- if($('#goalTip').length) new zui.Tooltip('#goalTip', {title: goalTip, trigger: 'hover', placement: 'top', type: 'black', 'className': 'border border-light'});
- if($('#foundBugTip').length) new zui.Tooltip('#foundBugTip', {title: foundBugTip, trigger: 'hover', placement: 'top', type: 'black', 'className': 'border border-light'});
- if($('#legacyBugTip').length) new zui.Tooltip('#legacyBugTip', {title: legacyBugTip, trigger: 'hover', placement: 'top', type: 'black', 'className': 'border border-light'});
- if($('#activatedBugTip').length) new zui.Tooltip('#activatedBugTip', {title: activatedBugTip, trigger: 'hover', placement: 'top', type: 'black', 'className': 'border border-light'});
- if($('#fromCaseBugTip').length) new zui.Tooltip('#fromCaseBugTip', {title: fromCaseBugTip, trigger: 'hover', placement: 'top', type: 'black', 'className': 'border border-light'});
-});
-
/**
* Refresh page.
*
diff --git a/module/testreport/lang/zh-cn.php b/module/testreport/lang/zh-cn.php
index e44493778a..42e3f37893 100644
--- a/module/testreport/lang/zh-cn.php
+++ b/module/testreport/lang/zh-cn.php
@@ -90,9 +90,9 @@ $lang->testreport->hiddenCase = "隐藏 %s 个用例";
$lang->testreport->goalTip = "该版本所属{$lang->execution->common}的描述信息";
$lang->testreport->bugSummary = <<%s个Bug ,
-遗留%s个Bug 。
-重新激活%s个Bug 。
-用例执行产生%s个Bug 。
+共发现%s个Bug ,
+遗留%s个Bug 。
+重新激活%s个Bug 。
+用例执行产生%s个Bug 。
有效Bug率(方案为已解决或延期 / 状态为已解决或已关闭):%s,用例发现Bug率(用例创建的Bug / 发现Bug数):%s
EOD;
diff --git a/module/testreport/ui/create.html.php b/module/testreport/ui/create.html.php
index 4855380962..09557d8fff 100644
--- a/module/testreport/ui/create.html.php
+++ b/module/testreport/ui/create.html.php
@@ -16,11 +16,6 @@ jsVar('objectID', $objectID);
jsVar('objectType', $objectType);
jsVar('extra', $extra);
jsVar('reportID', !empty($report->id) ? $report->id : 0);
-jsVar('goalTip', $lang->testreport->goalTip);
-jsVar('foundBugTip', $lang->testreport->foundBugTip);
-jsVar('legacyBugTip', $lang->testreport->legacyBugTip);
-jsVar('activatedBugTip', $lang->testreport->activatedBugTip);
-jsVar('fromCaseBugTip', $lang->testreport->fromCaseBugTip);
$caseCharts = array();
foreach($charts as $chartType => $chartOption)
@@ -466,9 +461,8 @@ panel
icon
(
'help',
- setID('goalTip'),
setClass('text-light mr-0.5'),
- setData('toggle', 'tooltip'),
+ setData(array('toggle' => 'tooltip', 'title' => $lang->testreport->goalTip))
),
strip_tags($execution->desc)
)
diff --git a/module/testreport/ui/edit.html.php b/module/testreport/ui/edit.html.php
index a05ebb8d80..39fc201ee6 100644
--- a/module/testreport/ui/edit.html.php
+++ b/module/testreport/ui/edit.html.php
@@ -9,11 +9,6 @@ declare(strict_types=1);
* @link https://www.zentao.net
*/
namespace zin;
-jsVar('goalTip', $lang->testreport->goalTip);
-jsVar('foundBugTip', $lang->testreport->foundBugTip);
-jsVar('legacyBugTip', $lang->testreport->legacyBugTip);
-jsVar('activatedBugTip', $lang->testreport->activatedBugTip);
-jsVar('fromCaseBugTip', $lang->testreport->fromCaseBugTip);
$caseCharts = array();
foreach($charts as $chartType => $chartOption)
@@ -429,9 +424,8 @@ panel
icon
(
'help',
- setID('goalTip'),
setClass('text-light mr-0.5'),
- setData('toggle', 'tooltip'),
+ setData(array('toggle' => 'tooltip', 'title' => $lang->testreport->goalTip))
),
strip_tags($execution->desc)
)
diff --git a/module/testreport/ui/view.html.php b/module/testreport/ui/view.html.php
index 3f4c649669..eaa08ee61a 100644
--- a/module/testreport/ui/view.html.php
+++ b/module/testreport/ui/view.html.php
@@ -9,12 +9,6 @@ declare(strict_types=1);
* @link https://www.zentao.net
*/
namespace zin;
-jsVar('goalTip', $lang->testreport->goalTip);
-jsVar('foundBugTip', $lang->testreport->foundBugTip);
-jsVar('legacyBugTip', $lang->testreport->legacyBugTip);
-jsVar('activatedBugTip', $lang->testreport->activatedBugTip);
-jsVar('fromCaseBugTip', $lang->testreport->fromCaseBugTip);
-
$this->session->notHead ? null : detailHeader
(
to::title
@@ -376,9 +370,8 @@ detailBody
icon
(
'help',
- setID('goalTip'),
setClass('text-light mr-0.5'),
- setData('toggle', 'tooltip'),
+ setData(array('toggle' => 'tooltip', 'title' => $lang->testreport->goalTip))
),
strip_tags($execution->desc)
) : null,
diff --git a/module/transfer/model.php b/module/transfer/model.php
index 76aa30c910..a6b6a29c6b 100644
--- a/module/transfer/model.php
+++ b/module/transfer/model.php
@@ -147,6 +147,7 @@ class transferModel extends model
$transferFieldList = $this->transferConfig->fieldList; //生成一个完整的fieldList结构。
if(is_string($this->moduleConfig->dateFields)) $this->moduleConfig->dateFields = explode(',', $this->moduleConfig->dateFields);
if(is_string($this->moduleConfig->datetimeFields)) $this->moduleConfig->datetimeFields = explode(',', $this->moduleConfig->datetimeFields);
+ if(is_string($this->moduleConfig->textareaFields)) $this->moduleConfig->textareaFields = explode(',', $this->moduleConfig->textareaFields);
$fieldList = array();
/* build module fieldList. */
@@ -173,6 +174,7 @@ class transferModel extends model
if(in_array($field, $this->moduleConfig->dateFields)) $moduleFieldList['control'] = 'datePicker';
if(in_array($field, $this->moduleConfig->datetimeFields)) $moduleFieldList['control'] = 'datetimePicker';
+ if(in_array($field, $this->moduleConfig->textareaFields)) $moduleFieldList['control'] = 'textarea';
$moduleFieldList['multiple'] = $moduleFieldList['control'] == 'multiple';
if($moduleFieldList['control'] == 'select' || $moduleFieldList['control'] == 'multiple') $moduleFieldList['control'] = 'picker';
@@ -444,6 +446,7 @@ class transferModel extends model
$this->moduleConfig->sysLangFields = isset($moduleConfig->sysLangFields) ? $moduleConfig->sysLangFields : $transferConfig->sysLangFields;
$this->moduleConfig->sysDataFields = isset($moduleConfig->sysDataFields) ? $moduleConfig->sysDataFields : $transferConfig->sysDataFields;
$this->moduleConfig->datetimeFields = isset($moduleConfig->datetimeFields) ? $moduleConfig->datetimeFields : $transferConfig->datetimeFields;
+ $this->moduleConfig->textareaFields = isset($moduleConfig->textareaFields) ? $moduleConfig->textareaFields : $transferConfig->textareaFields;
}
/**
diff --git a/module/upgrade/config.php b/module/upgrade/config.php
index 84246759b8..18c718542b 100644
--- a/module/upgrade/config.php
+++ b/module/upgrade/config.php
@@ -55,7 +55,8 @@ $config->upgrade->maxVersion['max5_3'] = '20_4';
$config->upgrade->maxVersion['max4_13'] = '18_13';
$config->upgrade->maxVersion['max5_4'] = '20_5';
$config->upgrade->maxVersion['max5_5'] = '20_6';
-$config->upgrade->maxVersion['max5_6'] = '20_7'; // max insert position.
+$config->upgrade->maxVersion['max5_6'] = '20_7';
+$config->upgrade->maxVersion['max5_6_1'] = '20_7_1'; // max insert position.
$config->upgrade->bizVersion = array();
$config->upgrade->bizVersion['biz1_0'] = '9_5_1';
@@ -149,7 +150,8 @@ $config->upgrade->bizVersion['biz10_3'] = '20_4';
$config->upgrade->bizVersion['biz8_13'] = '18_13';
$config->upgrade->bizVersion['biz10_4'] = '20_5';
$config->upgrade->bizVersion['biz10_5'] = '20_6';
-$config->upgrade->bizVersion['biz10_6'] = '20_7'; // biz insert position.
+$config->upgrade->bizVersion['biz10_6'] = '20_7';
+$config->upgrade->bizVersion['biz10_6_1'] = '20_7_1'; // biz insert position.
$config->upgrade->proVersion = array();
$config->upgrade->proVersion['pro1_0'] = '3_1';
@@ -280,7 +282,8 @@ $config->upgrade->ipdVersion['ipd2_3'] = '20_4';
$config->upgrade->ipdVersion['ipd1_5'] = '18_13';
$config->upgrade->ipdVersion['ipd2_4'] = '20_5';
$config->upgrade->ipdVersion['ipd2_5'] = '20_6';
-$config->upgrade->ipdVersion['ipd2_6'] = '20_7'; // ipd insert position.
+$config->upgrade->ipdVersion['ipd2_6'] = '20_7';
+$config->upgrade->ipdVersion['ipd2_6_1'] = '20_7_1'; // ipd insert position.
$config->upgrade->lowerTables = array();
$config->upgrade->lowerTables[$config->db->prefix . 'caseStep'] = $config->db->prefix . 'casestep';
diff --git a/module/upgrade/lang/version.php b/module/upgrade/lang/version.php
index 059f202280..653b8b3ded 100644
--- a/module/upgrade/lang/version.php
+++ b/module/upgrade/lang/version.php
@@ -200,7 +200,8 @@ $lang->upgrade->fromVersions['20_3_0'] = '20.3.0';
$lang->upgrade->fromVersions['20_4'] = '20.4';
$lang->upgrade->fromVersions['20_5'] = '20.5';
$lang->upgrade->fromVersions['20_6'] = '20.6';
-$lang->upgrade->fromVersions['20_7'] = '20.7'; // pms insert position.
+$lang->upgrade->fromVersions['20_7'] = '20.7';
+$lang->upgrade->fromVersions['20_7_1'] = '20.7.1'; // pms insert position.
global $config;
/* Lite. */
@@ -401,7 +402,8 @@ $lang->upgrade->fromVersions['biz10_2_0'] = 'Biz10.2.0';
$lang->upgrade->fromVersions['biz10_3'] = 'Biz10.3';
$lang->upgrade->fromVersions['biz10_4'] = 'Biz10.4';
$lang->upgrade->fromVersions['biz10_5'] = 'Biz10.5';
-$lang->upgrade->fromVersions['biz10_6'] = 'Biz10.6'; // biz insert position.
+$lang->upgrade->fromVersions['biz10_6'] = 'Biz10.6';
+$lang->upgrade->fromVersions['biz10_6_1'] = 'Biz10.6.1'; // biz insert position.
/* Max. */
$lang->upgrade->fromVersions['max2_0_beta4'] = 'Max2.0.beta4';
@@ -460,7 +462,8 @@ $lang->upgrade->fromVersions['max5_2_0'] = 'Max5.2.0';
$lang->upgrade->fromVersions['max5_3'] = 'Max5.3';
$lang->upgrade->fromVersions['max5_4'] = 'Max5.4';
$lang->upgrade->fromVersions['max5_5'] = 'Max5.5';
-$lang->upgrade->fromVersions['max5_6'] = 'Max5.6'; // max insert position.
+$lang->upgrade->fromVersions['max5_6'] = 'Max5.6';
+$lang->upgrade->fromVersions['max5_6_1'] = 'Max5.6.1'; // max insert position.
/* Ipd */
$lang->upgrade->fromVersions['ipd1_0_beta1'] = 'Ipd1.0.beta1';
@@ -480,4 +483,5 @@ $lang->upgrade->fromVersions['ipd2_1_0'] = 'Ipd2.1.0';
$lang->upgrade->fromVersions['ipd2_2_0'] = 'Ipd2.2.0';
$lang->upgrade->fromVersions['ipd2_3'] = 'Ipd2.3';
$lang->upgrade->fromVersions['ipd2_4'] = 'Ipd2.4';
-$lang->upgrade->fromVersions['ipd2_5'] = 'Ipd2.5'; // ipd insert position.
+$lang->upgrade->fromVersions['ipd2_5'] = 'Ipd2.5';
+$lang->upgrade->fromVersions['ipd2_6'] = 'Ipd2.6'; // ipd insert position.
diff --git a/module/user/control.php b/module/user/control.php
index 1d2b8ab22a..6d9533be34 100755
--- a/module/user/control.php
+++ b/module/user/control.php
@@ -720,6 +720,7 @@ class user extends control
helper::setcookie('tab', '', time());
$loginExpired = !(preg_match("/(m=|\/)(index)(&f=|-)(index)(&|-|\.)?/", strtolower($this->referer), $output) || $this->referer == $this->config->webRoot || empty($this->referer) || preg_match("/\/www\/$/", strtolower($this->referer), $output));
+ if($this->cookie->logout) $loginExpired = false;
$this->view->title = $this->lang->user->login;
$this->view->plugins = $this->loadModel('extension')->getExpiringPlugins(true);
@@ -792,6 +793,7 @@ class user extends control
helper::setcookie('za', '', time() - 3600);
helper::setcookie('zp', '', time() - 3600);
helper::setcookie('tab', '', time() - 3600);
+ helper::setcookie('logout', '1', 0);
$_SESSION = array(); // Clear session in roadrunner.
session_destroy();
@@ -830,8 +832,7 @@ class user extends control
if(dao::isError()) return $this->send(array('result' => 'fail', 'message' => dao::getError()));
if(!$result) return $this->send(array('result' => 'fail', 'message' => $this->lang->user->resetFail));
- $referer = helper::safe64Encode($this->createLink('index', 'index'));
- return $this->send(array('result' => 'success', 'message' => $this->lang->user->resetSuccess, 'locate' => inlink('logout', 'referer=' . $referer)));
+ return $this->send(array('result' => 'success', 'message' => $this->lang->user->resetSuccess, 'locate' => inlink('login')));
}
/* 移除真实路径以确保安全。*/
diff --git a/module/user/js/deny.ui.js b/module/user/js/deny.ui.js
index c66de8ded0..2cf864c268 100644
--- a/module/user/js/deny.ui.js
+++ b/module/user/js/deny.ui.js
@@ -6,3 +6,13 @@ window.locateLogin = function(obj)
if(typeof data.load != 'undefined') top.location.href = data.load;
})
}
+
+window.checkGoBackBtn = function()
+{
+ if(window.top === window) return;
+ const historyState = top.window.history.state;
+ const canGoBack = historyState && historyState.prev && historyState.prev.code === $.apps.currentCode;
+ if(canGoBack) return;
+ $('.go-back-btn').hide();
+ $('.close-app-btn').removeClass('hidden').on('click', () => $.apps.closeApp($.apps.currentCode));
+};
diff --git a/module/user/ui/deny.html.php b/module/user/ui/deny.html.php
index a12d220fe8..15340f1d5e 100644
--- a/module/user/ui/deny.html.php
+++ b/module/user/ui/deny.html.php
@@ -45,7 +45,8 @@ panel
set::title($app->user->account . ' ' . $lang->user->deny),
set::footerActions
(array(
- $referer ? array('url' => helper::safe64Decode($referer), 'text' => $lang->user->goback) : array('back' => 'APP', 'text' => $lang->user->goback),
+ array('text' => $lang->close, 'class' => 'close-app-btn hidden'),
+ $referer ? array('url' => helper::safe64Decode($referer), 'text' => $lang->user->goback) : array('back' => 'APP', 'text' => $lang->user->goback, 'class' => 'go-back-btn'),
array('data-url' => createLink('user', 'logout', "referer=" . helper::safe64Encode($denyPage)), 'class' => 'primary re-login-btn', 'text' => $lang->user->relogin, 'onclick' => 'locateLogin(this)')
)),
set::footerClass('justify-center'),
@@ -54,7 +55,8 @@ panel
setClass('alert'),
icon(setClass('icon-3x alert-icon'), set::style(array('opacity' => '0.6')), 'exclamation-sign'),
div(html($denyContent))
- )
+ ),
+ on::init()->call('checkGoBackBtn')
);
render();
diff --git a/module/user/zen.php b/module/user/zen.php
index 5e012d6d16..387318af8c 100644
--- a/module/user/zen.php
+++ b/module/user/zen.php
@@ -163,6 +163,7 @@ class userZen extends user
/* 获取用户所属权限组、权限和视图,记录日志并发放登录积分。*/
/* Get user's group, priv and view, save log and give login score. */
+ helper::setcookie('logout', false, 0);
$user = $this->user->login($user, true, $this->post->keepLogin);
/* 以 json 格式返回用户数据。*/
@@ -334,6 +335,8 @@ class userZen extends user
*/
public function responseForLogon(string $referer, string $viewType, string $loginLink, string $denyLink, string $locateReferer, string $locateWebRoot): array
{
+ helper::setcookie('logout', false, 0);
+
/* 以 json 格式返回用户数据。*/
/* Return user data in json format. */
if($viewType == 'json') return array('status' => 'success', 'user' => $this->getUserForJSON($this->app->user));
diff --git a/test/lib/webdriver/webdriver.class.php b/test/lib/webdriver/webdriver.class.php
index 4829dc5579..9e5e307614 100644
--- a/test/lib/webdriver/webdriver.class.php
+++ b/test/lib/webdriver/webdriver.class.php
@@ -892,7 +892,6 @@ class dom
}
}
-
/**
* Get element's coordinate on page.
*
@@ -1162,4 +1161,17 @@ class dom
$this->driver->executeScript("return $('[name={$name}]').zui('datePicker').$.setValue('$value')");
return $this;
}
+
+ /**
+ * 获取picker控件的选项
+ * Get picker items.
+ *
+ * @param string $pickerName
+ * @access public
+ * @return void
+ */
+ public function getPickerItems($pickerName)
+ {
+ return $this->driver->executeScript('return $("[name=' . $pickerName . ']").zui("picker").options.items;');
+ }
}
diff --git a/www/js/zui3/zui.zentao.css b/www/js/zui3/zui.zentao.css
index c9243c2d3e..1db34cc556 100644
--- a/www/js/zui3/zui.zentao.css
+++ b/www/js/zui3/zui.zentao.css
@@ -1,2 +1,2 @@
-/*! tailwindcss v3.4.4 | MIT License | https://tailwindcss.com*/*,:after,:before{border-color:rgb(var(--color-gray-200-rgb));border-style:solid;border-width:0;box-sizing:border-box}:after,:before{--tw-content:""}:host,html{line-height:1.5;-webkit-text-size-adjust:100%;font-family:-apple-system,Noto Sans,Helvetica Neue,Helvetica,Nimbus Sans L,Arial,Liberation Sans,PingFang SC,Hiragino Sans GB,Noto Sans CJK SC,Source Han Sans SC,Source Han Sans CN,Microsoft YaHei,Wenquanyi Micro Hei,WenQuanYi Zen Hei,ST Heiti,SimHei,WenQuanYi Zen Hei Sharp,sans-serif;font-feature-settings:normal;font-variation-settings:normal;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-tap-highlight-color:transparent}body{line-height:inherit;margin:0}hr{border-top-width:1px;color:inherit;height:0}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,pre,samp{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace;font-feature-settings:normal;font-size:1em;font-variation-settings:normal}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}table{border-collapse:collapse;border-color:inherit;text-indent:0}button,input,optgroup,select,textarea{color:inherit;font-family:inherit;font-feature-settings:inherit;font-size:100%;font-variation-settings:inherit;font-weight:inherit;letter-spacing:inherit;line-height:inherit;margin:0;padding:0}button,select{text-transform:none}button,input:where([type=button]),input:where([type=reset]),input:where([type=submit]){-webkit-appearance:button;background-color:transparent;background-image:none}:-moz-focusring{outline:auto}:-moz-ui-invalid{box-shadow:none}progress{vertical-align:baseline}::-webkit-inner-spin-button,::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}summary{display:list-item}blockquote,dd,dl,figure,h1,h2,h3,h4,h5,h6,hr,p,pre{margin:0}fieldset{margin:0}fieldset,legend{padding:0}menu,ol,ul{list-style:none;margin:0;padding:0}dialog{padding:0}textarea{resize:vertical}input::-moz-placeholder,textarea::-moz-placeholder{color:rgb(var(--color-gray-400-rgb));opacity:1}input::placeholder,textarea::placeholder{color:rgb(var(--color-gray-400-rgb));opacity:1}[role=button],button{cursor:pointer}:disabled{cursor:default}audio,canvas,embed,iframe,img,object,svg,video{display:block;vertical-align:middle}img,video{height:auto;max-width:100%}[hidden]{display:none}:root{--screen-2xl:1720px;--color-gray-50:#fcfdfe;--color-gray-100:#eff1f3;--color-gray-200:#ebedf3;--color-gray-300:#d2d6e5;--color-gray-400:#b2b9c5;--color-gray-500:#64758b;--color-gray-600:#4a577f;--color-gray-700:#3d4667;--color-gray-800:#353d57;--color-gray-900:#30394a;--color-gray-950:#0b0f18;--color-gray-50-rgb:252,253,254;--color-gray-100-rgb:239,241,243;--color-gray-200-rgb:235,237,243;--color-gray-300-rgb:210,214,229;--color-gray-400-rgb:178,185,197;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:74,87,127;--color-gray-700-rgb:61,70,103;--color-gray-800-rgb:53,61,87;--color-gray-900-rgb:48,57,74;--color-gray-950-rgb:11,15,24;--color-primary-50:#eef6ff;--color-primary-100:#d9eaff;--color-primary-200:#bcdcff;--color-primary-300:#8ec6ff;--color-primary-400:#59a5ff;--color-primary-500:#3883fa;--color-primary-600:#2b67e5;--color-primary-700:#144ce1;--color-primary-800:#173db6;--color-primary-900:#19388f;--color-primary-950:#142457;--color-primary-50-rgb:238,246,255;--color-primary-100-rgb:217,234,255;--color-primary-200-rgb:188,220,255;--color-primary-300-rgb:142,198,255;--color-primary-400-rgb:89,165,255;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:43,103,229;--color-primary-700-rgb:20,76,225;--color-primary-800-rgb:23,61,182;--color-primary-900-rgb:25,56,143;--color-primary-950-rgb:20,36,87;--color-secondary-50:#e7f6ff;--color-secondary-100:#cdecff;--color-secondary-200:#9bd9ff;--color-secondary-300:#77cbff;--color-secondary-400:#60c2ff;--color-secondary-500:#37b2fe;--color-secondary-600:#18a6fd;--color-secondary-700:#1099ed;--color-secondary-800:#078ada;--color-secondary-900:#046bab;--color-secondary-950:#062a4b;--color-secondary-50-rgb:231,246,255;--color-secondary-100-rgb:205,236,255;--color-secondary-200-rgb:155,217,255;--color-secondary-300-rgb:119,203,255;--color-secondary-400-rgb:96,194,255;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:24,166,253;--color-secondary-700-rgb:16,153,237;--color-secondary-800-rgb:7,138,218;--color-secondary-900-rgb:4,107,171;--color-secondary-950-rgb:6,42,75;--color-success-50:#effaf6;--color-success-100:#d6f2e7;--color-success-200:#ade5ce;--color-success-300:#83d7b6;--color-success-400:#5aca9d;--color-success-500:#31bd85;--color-success-600:#2ba675;--color-success-700:#28996c;--color-success-800:#21805a;--color-success-900:#185e3b;--color-success-950:#0e3421;--color-success-50-rgb:239,250,246;--color-success-100-rgb:214,242,231;--color-success-200-rgb:173,229,206;--color-success-300-rgb:131,215,182;--color-success-400-rgb:90,202,157;--color-success-500-rgb:49,189,133;--color-success-600-rgb:43,166,117;--color-success-700-rgb:40,153,108;--color-success-800-rgb:33,128,90;--color-success-900-rgb:24,94,59;--color-success-950-rgb:14,52,33;--color-warning-50:#fff4ea;--color-warning-100:#ffecdb;--color-warning-200:#ffd2a9;--color-warning-300:#ffbc7e;--color-warning-400:#ffaf65;--color-warning-500:#ff9f46;--color-warning-600:#f38f19;--color-warning-700:#ed8307;--color-warning-800:#d17100;--color-warning-900:#af5f01;--color-warning-950:#441506;--color-warning-50-rgb:255,244,234;--color-warning-100-rgb:255,236,219;--color-warning-200-rgb:255,210,169;--color-warning-300-rgb:255,188,126;--color-warning-400-rgb:255,175,101;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:243,143,25;--color-warning-700-rgb:237,131,7;--color-warning-800-rgb:209,113,0;--color-warning-900-rgb:175,95,1;--color-warning-950-rgb:68,21,6;--color-danger-50:#ffebeb;--color-danger-100:#ffd5d5;--color-danger-200:#ffb1b1;--color-danger-300:#ff9292;--color-danger-400:#ff7c7c;--color-danger-500:#fc5959;--color-danger-600:#fb2b2b;--color-danger-700:#d91b1b;--color-danger-800:#ba1313;--color-danger-900:#a20606;--color-danger-950:#470808;--color-danger-50-rgb:255,235,235;--color-danger-100-rgb:255,213,213;--color-danger-200-rgb:255,177,177;--color-danger-300-rgb:255,146,146;--color-danger-400-rgb:255,124,124;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:251,43,43;--color-danger-700-rgb:217,27,27;--color-danger-800-rgb:186,19,19;--color-danger-900-rgb:162,6,6;--color-danger-950-rgb:71,8,8;--color-important-50:#fff8f5;--color-important-100:#ffe2d9;--color-important-200:#ffcebf;--color-important-300:#ffb29b;--color-important-400:#ff8c68;--color-important-500:#ff8058;--color-important-600:#ff6f42;--color-important-700:#ff4912;--color-important-800:#c83509;--color-important-900:#611700;--color-important-950:#440609;--color-important-50-rgb:255,248,245;--color-important-100-rgb:255,226,217;--color-important-200-rgb:255,206,191;--color-important-300-rgb:255,178,155;--color-important-400-rgb:255,140,104;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,111,66;--color-important-700-rgb:255,73,18;--color-important-800-rgb:200,53,9;--color-important-900-rgb:97,23,0;--color-important-950-rgb:68,6,9;--color-special-50:#efecfa;--color-special-100:#e4dff7;--color-special-200:#c4b6ff;--color-special-300:#a38cff;--color-special-400:#8a6ff5;--color-special-500:#8166ee;--color-special-600:#7055df;--color-special-700:#513baa;--color-special-800:#452da5;--color-special-900:#30216e;--color-special-950:#271560;--color-special-50-rgb:239,236,250;--color-special-100-rgb:228,223,247;--color-special-200-rgb:196,182,255;--color-special-300-rgb:163,140,255;--color-special-400-rgb:138,111,245;--color-special-500-rgb:129,102,238;--color-special-600-rgb:112,85,223;--color-special-700-rgb:81,59,170;--color-special-800-rgb:69,45,165;--color-special-900-rgb:48,33,110;--color-special-950-rgb:39,21,96;--color-inherit:inherit;--color-transparent:transparent;--color-current:currentColor;--color-black:#000;--color-white:#fff;--color-canvas:#fff;--color-canvas-light:#fff;--color-canvas-dark:#fcfdfe;--color-inverse:#000;--color-surface:#eff1f3;--color-surface-light:#fcfdfe;--color-surface-strong:#ebedf3;--color-fore:#30394a;--color-fore-in-light:#30394a;--color-fore-in-dark:#fff;--color-focus:#bcdcff;--color-link:#2b47a2;--color-link-hover:#144ce1;--color-link-visited:#6328a4;--color-link-active:#144ce1;--color-placeholder:#64758b;--color-border:#ebedf3;--color-border-strong:#d2d6e5;--color-border-light:#eff1f3;--color-black-rgb:0,0,0;--color-white-rgb:255,255,255;--color-canvas-rgb:255,255,255;--color-canvas-light-rgb:255,255,255;--color-canvas-dark-rgb:252,253,254;--color-inverse-rgb:0,0,0;--color-surface-rgb:239,241,243;--color-surface-light-rgb:252,253,254;--color-surface-strong-rgb:235,237,243;--color-fore-rgb:48,57,74;--color-fore-in-light-rgb:48,57,74;--color-fore-in-dark-rgb:255,255,255;--color-focus-rgb:188,220,255;--color-link-rgb:43,71,162;--color-link-hover-rgb:20,76,225;--color-link-visited-rgb:99,40,164;--color-link-active-rgb:20,76,225;--color-placeholder-rgb:100,117,139;--color-border-rgb:235,237,243;--color-border-strong-rgb:210,214,229;--color-border-light-rgb:239,241,243;--radius-none:0px;--radius-sm:0.0625rem;--radius:0.125rem;--radius-md:0.25rem;--radius-lg:0.375rem;--radius-xl:0.5rem;--radius-2xl:0.75rem;--radius-3xl:1rem;--radius-full:9999px;--shadow-sm:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--shadow-md:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--shadow-lg:0 5px 15px -3px rgba(0,0,0,.2),0 2px 6px -4px rgba(0,0,0,.15);--shadow-xl:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--shadow-2xl:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--shadow-inner:inset 0 2px 4px 0 rgba(0,0,0,.05);--shadow-none:none;--space:0.25rem;--font-size-article:0.875rem;--font-size-root:16px;--font-size-page-lineHeight:1.5384615385}.dark{--color-gray-50:#0b0f18;--color-gray-100:#30394a;--color-gray-200:#353d57;--color-gray-300:#3d4667;--color-gray-400:#4a577f;--color-gray-500:#64758b;--color-gray-600:#b2b9c5;--color-gray-700:#d2d6e5;--color-gray-800:#ebedf3;--color-gray-900:#eff1f3;--color-gray-950:#fcfdfe;--color-gray-50-rgb:11,15,24;--color-gray-100-rgb:48,57,74;--color-gray-200-rgb:53,61,87;--color-gray-300-rgb:61,70,103;--color-gray-400-rgb:74,87,127;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:178,185,197;--color-gray-700-rgb:210,214,229;--color-gray-800-rgb:235,237,243;--color-gray-900-rgb:239,241,243;--color-gray-950-rgb:252,253,254;--color-primary-50:#142457;--color-primary-100:#19388f;--color-primary-200:#173db6;--color-primary-300:#144ce1;--color-primary-400:#2b67e5;--color-primary-500:#3883fa;--color-primary-600:#59a5ff;--color-primary-700:#8ec6ff;--color-primary-800:#bcdcff;--color-primary-900:#d9eaff;--color-primary-950:#eef6ff;--color-primary-50-rgb:20,36,87;--color-primary-100-rgb:25,56,143;--color-primary-200-rgb:23,61,182;--color-primary-300-rgb:20,76,225;--color-primary-400-rgb:43,103,229;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:89,165,255;--color-primary-700-rgb:142,198,255;--color-primary-800-rgb:188,220,255;--color-primary-900-rgb:217,234,255;--color-primary-950-rgb:238,246,255;--color-secondary-50:#062a4b;--color-secondary-100:#046bab;--color-secondary-200:#078ada;--color-secondary-300:#1099ed;--color-secondary-400:#18a6fd;--color-secondary-500:#37b2fe;--color-secondary-600:#60c2ff;--color-secondary-700:#77cbff;--color-secondary-800:#9bd9ff;--color-secondary-900:#cdecff;--color-secondary-950:#e7f6ff;--color-secondary-50-rgb:6,42,75;--color-secondary-100-rgb:4,107,171;--color-secondary-200-rgb:7,138,218;--color-secondary-300-rgb:16,153,237;--color-secondary-400-rgb:24,166,253;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:96,194,255;--color-secondary-700-rgb:119,203,255;--color-secondary-800-rgb:155,217,255;--color-secondary-900-rgb:205,236,255;--color-secondary-950-rgb:231,246,255;--color-success-50:#0e3421;--color-success-100:#185e3b;--color-success-200:#21805a;--color-success-300:#28996c;--color-success-400:#2ba675;--color-success-500:#31bd85;--color-success-600:#5aca9d;--color-success-700:#83d7b6;--color-success-800:#ade5ce;--color-success-900:#d6f2e7;--color-success-950:#effaf6;--color-success-50-rgb:14,52,33;--color-success-100-rgb:24,94,59;--color-success-200-rgb:33,128,90;--color-success-300-rgb:40,153,108;--color-success-400-rgb:43,166,117;--color-success-500-rgb:49,189,133;--color-success-600-rgb:90,202,157;--color-success-700-rgb:131,215,182;--color-success-800-rgb:173,229,206;--color-success-900-rgb:214,242,231;--color-success-950-rgb:239,250,246;--color-warning-50:#441506;--color-warning-100:#af5f01;--color-warning-200:#d17100;--color-warning-300:#ed8307;--color-warning-400:#f38f19;--color-warning-500:#ff9f46;--color-warning-600:#ffaf65;--color-warning-700:#ffbc7e;--color-warning-800:#ffd2a9;--color-warning-900:#ffecdb;--color-warning-950:#fff4ea;--color-warning-50-rgb:68,21,6;--color-warning-100-rgb:175,95,1;--color-warning-200-rgb:209,113,0;--color-warning-300-rgb:237,131,7;--color-warning-400-rgb:243,143,25;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:255,175,101;--color-warning-700-rgb:255,188,126;--color-warning-800-rgb:255,210,169;--color-warning-900-rgb:255,236,219;--color-warning-950-rgb:255,244,234;--color-danger-50:#470808;--color-danger-100:#a20606;--color-danger-200:#ba1313;--color-danger-300:#d91b1b;--color-danger-400:#fb2b2b;--color-danger-500:#fc5959;--color-danger-600:#ff7c7c;--color-danger-700:#ff9292;--color-danger-800:#ffb1b1;--color-danger-900:#ffd5d5;--color-danger-950:#ffebeb;--color-danger-50-rgb:71,8,8;--color-danger-100-rgb:162,6,6;--color-danger-200-rgb:186,19,19;--color-danger-300-rgb:217,27,27;--color-danger-400-rgb:251,43,43;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:255,124,124;--color-danger-700-rgb:255,146,146;--color-danger-800-rgb:255,177,177;--color-danger-900-rgb:255,213,213;--color-danger-950-rgb:255,235,235;--color-important-50:#440609;--color-important-100:#611700;--color-important-200:#c83509;--color-important-300:#ff4912;--color-important-400:#ff6f42;--color-important-500:#ff8058;--color-important-600:#ff8c68;--color-important-700:#ffb29b;--color-important-800:#ffcebf;--color-important-900:#ffe2d9;--color-important-950:#fff8f5;--color-important-50-rgb:68,6,9;--color-important-100-rgb:97,23,0;--color-important-200-rgb:200,53,9;--color-important-300-rgb:255,73,18;--color-important-400-rgb:255,111,66;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,140,104;--color-important-700-rgb:255,178,155;--color-important-800-rgb:255,206,191;--color-important-900-rgb:255,226,217;--color-important-950-rgb:255,248,245;--color-special-50:#271560;--color-special-100:#30216e;--color-special-200:#452da5;--color-special-300:#513baa;--color-special-400:#7055df;--color-special-500:#8166ee;--color-special-600:#8a6ff5;--color-special-700:#a38cff;--color-special-800:#c4b6ff;--color-special-900:#e4dff7;--color-special-950:#efecfa;--color-special-50-rgb:39,21,96;--color-special-100-rgb:48,33,110;--color-special-200-rgb:69,45,165;--color-special-300-rgb:81,59,170;--color-special-400-rgb:112,85,223;--color-special-500-rgb:129,102,238;--color-special-600-rgb:138,111,245;--color-special-700-rgb:163,140,255;--color-special-800-rgb:196,182,255;--color-special-900-rgb:228,223,247;--color-special-950-rgb:239,236,250;--color-canvas:#0b0f18;--color-inverse:#fff;--color-surface:#353d57;--color-surface-light:#30394a;--color-surface-strong:#3d4667;--color-fore:#ebedf3;--color-focus:#173db6;--color-link:#59a5ff;--color-link-hover:#3883fa;--color-link-visited:#bcdcff;--color-link-active:#bcdcff;--color-placeholder:#4a577f;--color-border:#353d57;--color-border-strong:#3d4667;--color-border-light:#30394a;--color-canvas-rgb:11,15,24;--color-inverse-rgb:255,255,255;--color-surface-rgb:53,61,87;--color-surface-light-rgb:48,57,74;--color-surface-strong-rgb:61,70,103;--color-fore-rgb:235,237,243;--color-focus-rgb:23,61,182;--color-link-rgb:89,165,255;--color-link-hover-rgb:56,131,250;--color-link-visited-rgb:188,220,255;--color-link-active-rgb:188,220,255;--color-placeholder-rgb:74,87,127;--color-border-rgb:53,61,87;--color-border-strong-rgb:61,70,103;--color-border-light-rgb:48,57,74}.light-in-dark{--color-gray-50:#fcfdfe;--color-gray-100:#eff1f3;--color-gray-200:#ebedf3;--color-gray-300:#d2d6e5;--color-gray-400:#b2b9c5;--color-gray-500:#64758b;--color-gray-600:#4a577f;--color-gray-700:#3d4667;--color-gray-800:#353d57;--color-gray-900:#30394a;--color-gray-950:#0b0f18;--color-gray-50-rgb:252,253,254;--color-gray-100-rgb:239,241,243;--color-gray-200-rgb:235,237,243;--color-gray-300-rgb:210,214,229;--color-gray-400-rgb:178,185,197;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:74,87,127;--color-gray-700-rgb:61,70,103;--color-gray-800-rgb:53,61,87;--color-gray-900-rgb:48,57,74;--color-gray-950-rgb:11,15,24;--color-primary-50:#eef6ff;--color-primary-100:#d9eaff;--color-primary-200:#bcdcff;--color-primary-300:#8ec6ff;--color-primary-400:#59a5ff;--color-primary-500:#3883fa;--color-primary-600:#2b67e5;--color-primary-700:#144ce1;--color-primary-800:#173db6;--color-primary-900:#19388f;--color-primary-950:#142457;--color-primary-50-rgb:238,246,255;--color-primary-100-rgb:217,234,255;--color-primary-200-rgb:188,220,255;--color-primary-300-rgb:142,198,255;--color-primary-400-rgb:89,165,255;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:43,103,229;--color-primary-700-rgb:20,76,225;--color-primary-800-rgb:23,61,182;--color-primary-900-rgb:25,56,143;--color-primary-950-rgb:20,36,87;--color-secondary-50:#e7f6ff;--color-secondary-100:#cdecff;--color-secondary-200:#9bd9ff;--color-secondary-300:#77cbff;--color-secondary-400:#60c2ff;--color-secondary-500:#37b2fe;--color-secondary-600:#18a6fd;--color-secondary-700:#1099ed;--color-secondary-800:#078ada;--color-secondary-900:#046bab;--color-secondary-950:#062a4b;--color-secondary-50-rgb:231,246,255;--color-secondary-100-rgb:205,236,255;--color-secondary-200-rgb:155,217,255;--color-secondary-300-rgb:119,203,255;--color-secondary-400-rgb:96,194,255;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:24,166,253;--color-secondary-700-rgb:16,153,237;--color-secondary-800-rgb:7,138,218;--color-secondary-900-rgb:4,107,171;--color-secondary-950-rgb:6,42,75;--color-success-50:#effaf6;--color-success-100:#d6f2e7;--color-success-200:#ade5ce;--color-success-300:#83d7b6;--color-success-400:#5aca9d;--color-success-500:#31bd85;--color-success-600:#2ba675;--color-success-700:#28996c;--color-success-800:#21805a;--color-success-900:#185e3b;--color-success-950:#0e3421;--color-success-50-rgb:239,250,246;--color-success-100-rgb:214,242,231;--color-success-200-rgb:173,229,206;--color-success-300-rgb:131,215,182;--color-success-400-rgb:90,202,157;--color-success-500-rgb:49,189,133;--color-success-600-rgb:43,166,117;--color-success-700-rgb:40,153,108;--color-success-800-rgb:33,128,90;--color-success-900-rgb:24,94,59;--color-success-950-rgb:14,52,33;--color-warning-50:#fff4ea;--color-warning-100:#ffecdb;--color-warning-200:#ffd2a9;--color-warning-300:#ffbc7e;--color-warning-400:#ffaf65;--color-warning-500:#ff9f46;--color-warning-600:#f38f19;--color-warning-700:#ed8307;--color-warning-800:#d17100;--color-warning-900:#af5f01;--color-warning-950:#441506;--color-warning-50-rgb:255,244,234;--color-warning-100-rgb:255,236,219;--color-warning-200-rgb:255,210,169;--color-warning-300-rgb:255,188,126;--color-warning-400-rgb:255,175,101;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:243,143,25;--color-warning-700-rgb:237,131,7;--color-warning-800-rgb:209,113,0;--color-warning-900-rgb:175,95,1;--color-warning-950-rgb:68,21,6;--color-danger-50:#ffebeb;--color-danger-100:#ffd5d5;--color-danger-200:#ffb1b1;--color-danger-300:#ff9292;--color-danger-400:#ff7c7c;--color-danger-500:#fc5959;--color-danger-600:#fb2b2b;--color-danger-700:#d91b1b;--color-danger-800:#ba1313;--color-danger-900:#a20606;--color-danger-950:#470808;--color-danger-50-rgb:255,235,235;--color-danger-100-rgb:255,213,213;--color-danger-200-rgb:255,177,177;--color-danger-300-rgb:255,146,146;--color-danger-400-rgb:255,124,124;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:251,43,43;--color-danger-700-rgb:217,27,27;--color-danger-800-rgb:186,19,19;--color-danger-900-rgb:162,6,6;--color-danger-950-rgb:71,8,8;--color-important-50:#fff8f5;--color-important-100:#ffe2d9;--color-important-200:#ffcebf;--color-important-300:#ffb29b;--color-important-400:#ff8c68;--color-important-500:#ff8058;--color-important-600:#ff6f42;--color-important-700:#ff4912;--color-important-800:#c83509;--color-important-900:#611700;--color-important-950:#440609;--color-important-50-rgb:255,248,245;--color-important-100-rgb:255,226,217;--color-important-200-rgb:255,206,191;--color-important-300-rgb:255,178,155;--color-important-400-rgb:255,140,104;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,111,66;--color-important-700-rgb:255,73,18;--color-important-800-rgb:200,53,9;--color-important-900-rgb:97,23,0;--color-important-950-rgb:68,6,9;--color-special-50:#efecfa;--color-special-100:#e4dff7;--color-special-200:#c4b6ff;--color-special-300:#a38cff;--color-special-400:#8a6ff5;--color-special-500:#8166ee;--color-special-600:#7055df;--color-special-700:#513baa;--color-special-800:#452da5;--color-special-900:#30216e;--color-special-950:#271560;--color-special-50-rgb:239,236,250;--color-special-100-rgb:228,223,247;--color-special-200-rgb:196,182,255;--color-special-300-rgb:163,140,255;--color-special-400-rgb:138,111,245;--color-special-500-rgb:129,102,238;--color-special-600-rgb:112,85,223;--color-special-700-rgb:81,59,170;--color-special-800-rgb:69,45,165;--color-special-900-rgb:48,33,110;--color-special-950-rgb:39,21,96;--color-inherit:inherit;--color-transparent:transparent;--color-current:currentColor;--color-black:#000;--color-white:#fff;--color-canvas:#fff;--color-canvas-light:#fff;--color-canvas-dark:#fcfdfe;--color-inverse:#000;--color-surface:#eff1f3;--color-surface-light:#fcfdfe;--color-surface-strong:#ebedf3;--color-fore:#30394a;--color-fore-in-light:#30394a;--color-fore-in-dark:#fff;--color-focus:#bcdcff;--color-link:#2b47a2;--color-link-hover:#144ce1;--color-link-visited:#6328a4;--color-link-active:#144ce1;--color-placeholder:#64758b;--color-border:#ebedf3;--color-border-strong:#d2d6e5;--color-border-light:#eff1f3;--color-black-rgb:0,0,0;--color-white-rgb:255,255,255;--color-canvas-rgb:255,255,255;--color-canvas-light-rgb:255,255,255;--color-canvas-dark-rgb:252,253,254;--color-inverse-rgb:0,0,0;--color-surface-rgb:239,241,243;--color-surface-light-rgb:252,253,254;--color-surface-strong-rgb:235,237,243;--color-fore-rgb:48,57,74;--color-fore-in-light-rgb:48,57,74;--color-fore-in-dark-rgb:255,255,255;--color-focus-rgb:188,220,255;--color-link-rgb:43,71,162;--color-link-hover-rgb:20,76,225;--color-link-visited-rgb:99,40,164;--color-link-active-rgb:20,76,225;--color-placeholder-rgb:100,117,139;--color-border-rgb:235,237,243;--color-border-strong-rgb:210,214,229;--color-border-light-rgb:239,241,243}body{--btn-bg:var(--color-gray-50)}@media (prefers-color-scheme:dark){.dark-auto{--color-gray-50:#0b0f18;--color-gray-100:#30394a;--color-gray-200:#353d57;--color-gray-300:#3d4667;--color-gray-400:#4a577f;--color-gray-500:#64758b;--color-gray-600:#b2b9c5;--color-gray-700:#d2d6e5;--color-gray-800:#ebedf3;--color-gray-900:#eff1f3;--color-gray-950:#fcfdfe;--color-gray-50-rgb:11,15,24;--color-gray-100-rgb:48,57,74;--color-gray-200-rgb:53,61,87;--color-gray-300-rgb:61,70,103;--color-gray-400-rgb:74,87,127;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:178,185,197;--color-gray-700-rgb:210,214,229;--color-gray-800-rgb:235,237,243;--color-gray-900-rgb:239,241,243;--color-gray-950-rgb:252,253,254;--color-primary-50:#142457;--color-primary-100:#19388f;--color-primary-200:#173db6;--color-primary-300:#144ce1;--color-primary-400:#2b67e5;--color-primary-500:#3883fa;--color-primary-600:#59a5ff;--color-primary-700:#8ec6ff;--color-primary-800:#bcdcff;--color-primary-900:#d9eaff;--color-primary-950:#eef6ff;--color-primary-50-rgb:20,36,87;--color-primary-100-rgb:25,56,143;--color-primary-200-rgb:23,61,182;--color-primary-300-rgb:20,76,225;--color-primary-400-rgb:43,103,229;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:89,165,255;--color-primary-700-rgb:142,198,255;--color-primary-800-rgb:188,220,255;--color-primary-900-rgb:217,234,255;--color-primary-950-rgb:238,246,255;--color-secondary-50:#062a4b;--color-secondary-100:#046bab;--color-secondary-200:#078ada;--color-secondary-300:#1099ed;--color-secondary-400:#18a6fd;--color-secondary-500:#37b2fe;--color-secondary-600:#60c2ff;--color-secondary-700:#77cbff;--color-secondary-800:#9bd9ff;--color-secondary-900:#cdecff;--color-secondary-950:#e7f6ff;--color-secondary-50-rgb:6,42,75;--color-secondary-100-rgb:4,107,171;--color-secondary-200-rgb:7,138,218;--color-secondary-300-rgb:16,153,237;--color-secondary-400-rgb:24,166,253;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:96,194,255;--color-secondary-700-rgb:119,203,255;--color-secondary-800-rgb:155,217,255;--color-secondary-900-rgb:205,236,255;--color-secondary-950-rgb:231,246,255;--color-success-50:#0e3421;--color-success-100:#185e3b;--color-success-200:#21805a;--color-success-300:#28996c;--color-success-400:#2ba675;--color-success-500:#31bd85;--color-success-600:#5aca9d;--color-success-700:#83d7b6;--color-success-800:#ade5ce;--color-success-900:#d6f2e7;--color-success-950:#effaf6;--color-success-50-rgb:14,52,33;--color-success-100-rgb:24,94,59;--color-success-200-rgb:33,128,90;--color-success-300-rgb:40,153,108;--color-success-400-rgb:43,166,117;--color-success-500-rgb:49,189,133;--color-success-600-rgb:90,202,157;--color-success-700-rgb:131,215,182;--color-success-800-rgb:173,229,206;--color-success-900-rgb:214,242,231;--color-success-950-rgb:239,250,246;--color-warning-50:#441506;--color-warning-100:#af5f01;--color-warning-200:#d17100;--color-warning-300:#ed8307;--color-warning-400:#f38f19;--color-warning-500:#ff9f46;--color-warning-600:#ffaf65;--color-warning-700:#ffbc7e;--color-warning-800:#ffd2a9;--color-warning-900:#ffecdb;--color-warning-950:#fff4ea;--color-warning-50-rgb:68,21,6;--color-warning-100-rgb:175,95,1;--color-warning-200-rgb:209,113,0;--color-warning-300-rgb:237,131,7;--color-warning-400-rgb:243,143,25;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:255,175,101;--color-warning-700-rgb:255,188,126;--color-warning-800-rgb:255,210,169;--color-warning-900-rgb:255,236,219;--color-warning-950-rgb:255,244,234;--color-danger-50:#470808;--color-danger-100:#a20606;--color-danger-200:#ba1313;--color-danger-300:#d91b1b;--color-danger-400:#fb2b2b;--color-danger-500:#fc5959;--color-danger-600:#ff7c7c;--color-danger-700:#ff9292;--color-danger-800:#ffb1b1;--color-danger-900:#ffd5d5;--color-danger-950:#ffebeb;--color-danger-50-rgb:71,8,8;--color-danger-100-rgb:162,6,6;--color-danger-200-rgb:186,19,19;--color-danger-300-rgb:217,27,27;--color-danger-400-rgb:251,43,43;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:255,124,124;--color-danger-700-rgb:255,146,146;--color-danger-800-rgb:255,177,177;--color-danger-900-rgb:255,213,213;--color-danger-950-rgb:255,235,235;--color-important-50:#440609;--color-important-100:#611700;--color-important-200:#c83509;--color-important-300:#ff4912;--color-important-400:#ff6f42;--color-important-500:#ff8058;--color-important-600:#ff8c68;--color-important-700:#ffb29b;--color-important-800:#ffcebf;--color-important-900:#ffe2d9;--color-important-950:#fff8f5;--color-important-50-rgb:68,6,9;--color-important-100-rgb:97,23,0;--color-important-200-rgb:200,53,9;--color-important-300-rgb:255,73,18;--color-important-400-rgb:255,111,66;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,140,104;--color-important-700-rgb:255,178,155;--color-important-800-rgb:255,206,191;--color-important-900-rgb:255,226,217;--color-important-950-rgb:255,248,245;--color-special-50:#271560;--color-special-100:#30216e;--color-special-200:#452da5;--color-special-300:#513baa;--color-special-400:#7055df;--color-special-500:#8166ee;--color-special-600:#8a6ff5;--color-special-700:#a38cff;--color-special-800:#c4b6ff;--color-special-900:#e4dff7;--color-special-950:#efecfa;--color-special-50-rgb:39,21,96;--color-special-100-rgb:48,33,110;--color-special-200-rgb:69,45,165;--color-special-300-rgb:81,59,170;--color-special-400-rgb:112,85,223;--color-special-500-rgb:129,102,238;--color-special-600-rgb:138,111,245;--color-special-700-rgb:163,140,255;--color-special-800-rgb:196,182,255;--color-special-900-rgb:228,223,247;--color-special-950-rgb:239,236,250;--color-canvas:#0b0f18;--color-inverse:#fff;--color-surface:#353d57;--color-surface-light:#30394a;--color-surface-strong:#3d4667;--color-fore:#ebedf3;--color-focus:#173db6;--color-link:#59a5ff;--color-link-hover:#3883fa;--color-link-visited:#bcdcff;--color-link-active:#bcdcff;--color-placeholder:#4a577f;--color-border:#353d57;--color-border-strong:#3d4667;--color-border-light:#30394a;--color-canvas-rgb:11,15,24;--color-inverse-rgb:255,255,255;--color-surface-rgb:53,61,87;--color-surface-light-rgb:48,57,74;--color-surface-strong-rgb:61,70,103;--color-fore-rgb:235,237,243;--color-focus-rgb:23,61,182;--color-link-rgb:89,165,255;--color-link-hover-rgb:56,131,250;--color-link-visited-rgb:188,220,255;--color-link-active-rgb:188,220,255;--color-placeholder-rgb:74,87,127;--color-border-rgb:53,61,87;--color-border-strong-rgb:61,70,103;--color-border-light-rgb:48,57,74}}*,:after,:before{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity))}:focus-visible{outline-color:transparent}*,:after,:before{--tw-border-spacing-x:0;--tw-border-spacing-y:0;--tw-translate-x:0;--tw-translate-y:0;--tw-rotate:0;--tw-skew-x:0;--tw-skew-y:0;--tw-scale-x:1;--tw-scale-y:1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness:proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-color:rgba(59,130,246,.5);--tw-ring-offset-shadow:0 0 #0000;--tw-ring-shadow:0 0 #0000;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }::backdrop{--tw-border-spacing-x:0;--tw-border-spacing-y:0;--tw-translate-x:0;--tw-translate-y:0;--tw-rotate:0;--tw-skew-x:0;--tw-skew-y:0;--tw-scale-x:1;--tw-scale-y:1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness:proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-color:rgba(59,130,246,.5);--tw-ring-offset-shadow:0 0 #0000;--tw-ring-shadow:0 0 #0000;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }html{font-size:var(--font-size-root)}body{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));font-size:.8125rem;line-height:1.5384615385}.dark,body{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}:root{--font-h1-size:2.25rem;--article-p-space:0.5em;--article-heading-space:0.5em;--article-hr-space:1.5em;--article-cell-padding:0.25rem 0.75rem}a,a.disabled:hover{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity))}a:hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}a:focus-visible{outline-color:rgb(var(--color-focus-rgb));outline-offset:2px;outline-width:2px}.code,code{background-color:rgba(var(--color-important-500-rgb),.1);border-radius:var(--radius);padding-left:.25rem;padding-right:.25rem;--tw-text-opacity:1;color:rgba(var(--color-important-500-rgb),var(--tw-text-opacity))}pre{font-size:.75rem;line-height:1rem;overflow:auto;padding:.5rem}pre code{background-color:transparent;color:inherit;padding:0}samp,var{font-weight:700}.blockquote,blockquote{border-left-width:4px;font-size:.875rem;line-height:1.3rem;padding-left:.75rem;text-wrap:balance}.blockquote figcaption,blockquote figcaption{font-size:.75rem;line-height:1rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6{font-weight:700;line-height:1.5;text-wrap:balance}.h1,h1{font-size:1.75rem}.h2,h2{font-size:1.5rem}.h3,h3{font-size:1.25rem}.h4,h4{font-size:1rem}.h5,h5{font-size:.875rem}.h6,h6{font-size:.75rem}ul{list-style-type:disc}ol,ul{padding-left:1.5em}ol{list-style-type:decimal}dt{font-weight:700}dd{padding-left:2em}.article{color:var(--font-size-article);-webkit-hyphens:auto;hyphens:auto;overflow-wrap:break-word}.article h1,.article h2,.article h3,.article h4{margin-bottom:var(--article-heading-space);margin-top:var(--article-heading-space)}.article audio,.article blockquote,.article figure,.article img,.article ol,.article p,.article table,.article ul,.article video{margin-bottom:var(--article-p-space);margin-top:var(--article-p-space)}.article p{min-height:1em}.article p:empty:before{content:" ";display:inline-block}.article hr{margin-bottom:var(--article-hr-space);margin-top:var(--article-hr-space)}.article table{border-width:1px}.article td,.article th{border-bottom-width:1px;padding:var(--article-cell-padding)}.article thead{background-color:var(--table-head-bg,var(--color-gray-100))}.article ol *,.article table *,.article ul *{margin-bottom:0;margin-top:0}.article pre{border-radius:var(--radius);border-width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity))}:root{--alert-bg:var(--color-surface)}.alert{align-items:center;background-color:var(--alert-bg);border-radius:var(--radius);display:flex;gap:.75rem;padding:.5rem .75rem}.alert-content{display:flex;flex:1 1 auto;flex-direction:column;gap:1rem}.alert-close{margin-bottom:-.375rem;margin-right:-.5rem;margin-top:-.375rem}.alert-link{color:inherit;font-weight:700}.alert-link:hover{color:inherit;text-decoration-line:underline}.alert-heading{font-weight:700;margin:0}.alert-text{flex:1 1 auto;white-space:pre-line}.alert-actions{align-items:center;display:flex;gap:.5rem}:root{--breadcrumb-divider:"/";--breadcrumb-divider-color:var(--color-gray-500);--breadcrumb-color-active:var(--color-gray-500)}.breadcrumb{display:flex;gap:1.25rem;list-style-type:none;padding-left:0}.breadcrumb>li{position:relative}.breadcrumb>li+li:before{color:var(--breadcrumb-divider-color);content:var(--breadcrumb-divider);display:block;left:-1.25rem;position:absolute;text-align:center;width:1.25rem}.breadcrumb>.active{color:var(--breadcrumb-color-active)}:root{--btn-radius:var(--radius);--btn-bg:var(--color-surface);--btn-border-color:var(--color-gray-300);--btn-height:2rem}.btn{align-items:center;background-color:var(--btn-bg);border-radius:var(--btn-radius);display:inline-flex;gap:.375rem;height:var(--btn-height);justify-content:center;padding-left:.75rem;padding-right:.75rem;white-space:nowrap;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--btn-border-color)}.btn,.btn-default:hover{color:inherit}.btn-link{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity));text-decoration-line:underline;text-underline-offset:2px;--tw-ring-color:transparent}.btn-link:visited{color:rgba(var(--color-link-visited-rgb),var(--tw-text-opacity))}.btn-link:hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}.btn-link{--btn-bg:transparent}.btn.size-xs,.size-xs>.btn{padding-left:.25rem;padding-right:.25rem;--btn-height:1.25rem}.btn.size-sm,.btn.size-xs,.size-sm>.btn,.size-xs>.btn{font-size:.75rem;line-height:1rem}.btn.size-sm,.size-sm>.btn{--btn-height:1.5rem}.btn.size-md,.btn.size-sm,.size-md>.btn,.size-sm>.btn{padding-left:.5rem;padding-right:.5rem}.btn.size-md,.size-md>.btn{--btn-height:1.75rem}.btn.size-lg,.size-lg>.btn{font-size:1rem;line-height:1.5rem;padding-left:1rem;padding-right:1rem;--btn-height:2.5rem}.btn.size-xl,.size-xl>.btn{font-size:1.125rem;line-height:1.75rem;padding-left:1.25rem;padding-right:1.25rem;--btn-height:3rem}.btn.square{aspect-ratio:1/1;gap:.125rem;padding-left:0;padding-right:0}@supports not (aspect-ratio:1/1){.btn.square{width:var(--btn-height)}}.btn.btn-caret{padding-left:.25rem;padding-right:.25rem}.btn.btn-wide{min-width:80px}:root{--checkbox-size:12px;--checkbox-color:var(--color-primary-500)}.checkbox,.radio{align-items:center;cursor:pointer;display:flex;gap:.375rem;min-height:20px}.checkbox>input[type=checkbox],.radio>input[type=radio]{accent-color:rgb(var(--color-primary-500-rgb));border-radius:var(--radius-lg)}.checkbox-primary,.radio-primary{display:flex;gap:.375rem;min-height:20px;position:relative}.checkbox-primary>input[type=checkbox],.radio-primary>input[type=radio]{bottom:0;left:0;opacity:0;position:absolute;right:0;top:0}.checkbox-primary>label,.radio-primary>label{cursor:pointer;padding-left:calc(var(--checkbox-size) + 8px);position:relative}.checkbox-primary>label:after,.checkbox-primary>label:before,.radio-primary>label:after,.radio-primary>label:before{display:block;height:var(--checkbox-size);left:0;position:absolute;transition-duration:.15s;transition-property:transform,background-color,color,opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:var(--checkbox-size);--tw-content:"";content:var(--tw-content);top:calc((20px - var(--checkbox-size))/2)}.checkbox-primary>label:before{border-radius:var(--radius-sm);border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.checkbox-primary>label:after{--tw-scale-x:.9;--tw-scale-y:.9;background-image:url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZmlsbD0iI2ZmZiIgZD0ibTkgMjAuNDItNi4yMS02LjIxIDIuODMtMi44M0w5IDE0Ljc3bDkuODgtOS44OSAyLjgzIDIuODN6Ii8+PC9zdmc+");transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.radio-primary>label:before{border-radius:var(--radius-full);border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.radio-primary>label:after{background-color:var(--checkbox-color);border-radius:var(--radius-full);opacity:0;--checkbox-radio-size:calc(var(--checkbox-size)*2/3);height:var(--checkbox-radio-size);left:calc((var(--checkbox-size) - var(--checkbox-radio-size))/2);top:calc((20px - var(--checkbox-radio-size))/2);width:var(--checkbox-radio-size)}.checkbox-primary>label:hover:before,.radio-primary>label:hover:before{border-color:var(--checkbox-color)}.checkbox-primary.focus>label:before,.checkbox-primary>input[type=checkbox]:focus+label:before,.radio-primary.focus>label:before,.radio-primary>input[type=radio]:focus+label:before{border-color:var(--checkbox-color);outline-color:rgb(var(--color-focus-rgb));outline-style:solid;outline-width:2px}.checkbox-primary.checked>label:before,.checkbox-primary>input[type=checkbox]:checked+label:before{background-color:var(--checkbox-color);border-color:var(--checkbox-color)}.radio-primary.checked>label:before,.radio-primary>input[type=radio]:checked+label:before{border-color:var(--checkbox-color)}.checkbox-primary.checked>label:after,.checkbox-primary>input[type=checkbox]:checked+label:after,.radio-primary.checked>label:after,.radio-primary>input[type=radio]:checked+label:after{opacity:1}.checkbox-primary.disabled>label,.checkbox-primary>input[type=checkbox]:disabled+label,.radio-primary.disabled>label,.radio-primary>input[type=radio]:disabled+label{cursor:not-allowed;opacity:.7;pointer-events:none;--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.checkbox-primary.indeterminate>label:after,.checkbox-primary>input[type=checkbox]:indeterminate+label:after{--tw-border-opacity:1;background-color:var(--checkbox-color);background-image:none;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity));border-width:calc((var(--checkbox-size) - 2px)/2) 2px;opacity:1}.check-list{align-items:flex-start;flex-direction:column;gap:.5rem}.check-list,.check-list-inline{display:flex;padding-bottom:.375rem;padding-top:.375rem}.check-list-inline{align-items:center;-moz-column-gap:1rem;column-gap:1rem;flex-direction:row;flex-wrap:wrap;row-gap:.5rem}.switch{display:flex;gap:.375rem;min-height:20px;padding-left:2.5rem;position:relative}.switch>input{bottom:0;left:0;opacity:0;position:absolute;right:0;top:0}.switch>label:after,.switch>label:before{border-radius:var(--radius-full);border-width:1px;height:1rem;left:0;position:absolute;top:.125rem;width:2rem;--tw-border-opacity:1;border-color:rgba(var(--color-border-strong-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));transition-duration:.3s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:"";content:var(--tw-content)}.switch>label:before{cursor:pointer;--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.switch>label:hover:before{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity))}.switch>label:after{height:.75rem;left:.125rem;top:.25rem;width:.75rem;--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.switch>input:checked+label:before{background-color:var(--checkbox-color);border-color:rgba(var(--color-inverse-rgb),.2)}.switch>input:checked+label:after{color:var(--checkbox-color);left:18px}.switch.focus>label:before,.switch>input:focus+label:before{border-color:var(--checkbox-color);outline-color:rgb(var(--color-focus-rgb));outline-style:solid;outline-width:2px}.switch.disabled>label:before,.switch>input:disabled+label:before{cursor:not-allowed;opacity:.7;pointer-events:none;--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}:root{--form-control-radius:var(--radius);--form-control-border:var(--color-border);--form-control-focus:var(--color-primary-500);--form-control-disabled:var(--color-surface);--form-control-readonly:var(--color-surface)}.dark{--form-control-border:var(--color-border-strong)}input::-moz-placeholder,textarea::-moz-placeholder{--tw-placeholder-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-placeholder-opacity))}input::placeholder,textarea::placeholder{--tw-placeholder-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-placeholder-opacity))}.form-control{border-radius:var(--form-control-radius);display:block;height:2rem;width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));outline-color:transparent;outline-style:solid;outline-width:1px;padding:.25rem .5rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--form-control-border);transition-duration:.15s;transition-property:outline,box-shadow;transition-timing-function:cubic-bezier(.4,0,.2,1)}.form-control.focus,.form-control:focus{outline-color:var(--form-control-focus);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-focus-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.3}.form-control.disabled,.form-control[disabled]{background-color:var(--form-control-disabled);opacity:1}.form-control.readonly,.form-control[readonly]{background-color:var(--form-control-readonly)}select{-webkit-appearance:none;background-image:url("data:image/gif;base64,R0lGODlhBwAEAIAAAMvQ2////yH5BAEAAAEALAAAAAAHAAQAAAIIhA+BGWoNWSgAOw==");background-position:right 8px top 50%;background-repeat:no-repeat;background-size:8px auto;padding-right:1rem}select.form-control[multiple]{background-image:none}textarea.form-control{height:auto;min-height:32px}input[type=file].form-control{padding:.125rem}input[type=file].form-control::-webkit-file-upload-button{-webkit-appearance:none;appearance:none;border-radius:inherit;border-style:none;cursor:pointer;height:1.75rem;padding-left:.5rem;padding-right:.5rem}input[type=file].form-control::-webkit-file-upload-button:hover{background-color:rgba(var(--color-black-rgb),.1)}.has-error .form-control,.has-error.form-control{--tw-ring-color:rgba(var(--color-danger-500-rgb),0.6)}.has-error .form-control.focus,.has-error .form-control:focus,.has-error.form-control.focus,.has-error.form-control:focus{outline-color:rgb(var(--color-danger-500-rgb));--tw-ring-color:rgba(var(--color-danger-500-rgb),0.1)}.has-warning .form-control,.has-warning.form-control{--tw-ring-color:rgba(var(--color-warning-500-rgb),0.6)}.has-warning .form-control.focus,.has-warning .form-control:focus,.has-warning.form-control.focus,.has-warning.form-control:focus{outline-color:rgb(var(--color-warning-500-rgb));--tw-ring-color:rgba(var(--color-warning-500-rgb),0.2)}.has-success .form-control,.has-success.form-control{--tw-ring-color:rgba(var(--color-success-500-rgb),0.6)}.has-success .form-control.focus,.has-success .form-control:focus,.has-success.form-control.focus,.has-success.form-control:focus{outline-color:rgb(var(--color-success-500-rgb));--tw-ring-color:rgba(var(--color-success-500-rgb),0.2)}.form-control.size-sm,.size-sm>.form-control{font-size:.75rem;height:1.5rem;line-height:1rem;padding-left:.5rem;padding-right:.5rem}.form-control.size-md,.size-md>.form-control{height:1.75rem;padding-left:.5rem;padding-right:.5rem}.form-control.size-lg,.size-lg>.form-control{font-size:1rem;height:2.5rem;line-height:1.5rem;padding-left:.75rem;padding-right:.75rem}:root{--input-group-addon-bg:var(--color-gray-50)}.input-group{align-items:stretch;display:flex}.input-group>.form-control,.input-group>.input-control{flex:1 1 auto;z-index:1}.input-group-addon{align-items:center;background-color:var(--input-group-addon-bg);border-radius:var(--form-control-radius);display:flex;flex:none;height:2rem;padding-left:.5rem;padding-right:.5rem;z-index:0;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--form-control-border)}.size-sm>.input-group-addon{font-size:.75rem;height:1.5rem;line-height:1rem;padding-left:.5rem;padding-right:.5rem}.size-lg>.input-group-addon{font-size:1rem;height:2.5rem;line-height:1.5rem;padding-left:.75rem;padding-right:.75rem}.input-group-control{flex:1 1 auto}.input-group>*+*,.input-group>*+* .form-control{border-bottom-left-radius:var(--radius-none);border-top-left-radius:var(--radius-none)}.input-group>:not(:last-child),.input-group>:not(:last-child) .form-control{border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none)}.input-group .btn:focus-visible,.input-group .form-control:focus{z-index:2}:root{--form-tip-color:var(--color-gray-400);--form-label-color:var(--color-gray-700);--form-horz-label-width:6rem;--form-grid-gap-x:1.25rem;--form-grid-gap-y:.75rem}.form{flex-direction:column;gap:1rem}.form,.form-label{display:flex}.form-label{align-items:center;color:var(--form-label-color);flex-direction:row;gap:.25rem;height:2rem;overflow:hidden;position:relative;text-overflow:ellipsis;white-space:nowrap}.form-label.required:after{content:"*";display:inline-block;margin-left:.25rem;--tw-translate-y:0.125rem;--tw-scale-x:1.25;--tw-scale-y:1.25;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.no-required .form-label.required:after{display:none}.form-label-actions{flex:1 1 auto;justify-content:flex-end}.form-label>.checkbox-primary{margin-left:.75rem}.form-tip{color:var(--form-tip-color);display:block;margin-top:.25rem}.has-error .form-tip{--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.has-warning .form-tip{--tw-text-opacity:1;color:rgba(var(--color-warning-500-rgb),var(--tw-text-opacity))}.has-success .form-tip{--tw-text-opacity:1;color:rgba(var(--color-success-500-rgb),var(--tw-text-opacity))}.form-actions{display:flex;flex-direction:row;gap:1rem;justify-content:center}.form-grid{--form-grid-gap-x-half:calc(var(--form-grid-gap-x)/2);--form-grid-gap-y-half:calc(var(--form-grid-gap-y)/2);align-items:flex-start;flex-direction:row;flex-wrap:wrap;gap:0}.form-grid .form-group{padding:var(--form-grid-gap-y-half) var(--form-grid-gap-x-half)}.form-grid .form-label.required:after{margin-left:.25rem;order:-9999}.form-grid .form-label .checkbox{margin-left:.75rem;margin-right:.75rem}.form-grid .has-wrap-after:after{display:block;width:100%;--tw-content:"";content:var(--tw-content)}.form-grid-wrap{width:100%}.form-grid-row{display:flex;flex-direction:row;padding-bottom:var(--form-grid-gap-y-half);padding-top:var(--form-grid-gap-y-half);position:relative;width:100%}.form-grid-col{padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half)}.form-grid .form-actions{gap:1.5rem;justify-content:center;padding:var(--form-grid-gap-y) var(--form-grid-gap-x-half);width:100%}.form-grid .form-actions.is-pinned{border-top-width:1px}.form-horz .form-row{align-items:flex-start;display:flex;flex-direction:row}.form-horz .form-group{align-items:flex-start;display:flex;flex:none;flex-direction:row;flex-wrap:wrap;min-height:32px;min-width:0;padding-left:var(--form-horz-label-width);position:relative}.form-horz .form-row .form-group{flex:1 1 auto}.form-horz .form-group[class*=" w-"],.form-horz .form-group[class^=w-]{flex:none}.form-horz .form-group>*{min-width:0}.form-horz .form-group.no-label{padding-left:0}.form-horz .form-group.no-label>.check-list-inline{padding-left:1rem;padding-right:1rem}.form-horz .form-label{justify-content:flex-end;left:0;padding-left:1rem;padding-right:.5rem;position:absolute;top:0;width:var(--form-horz-label-width)}.form-horz .form-label.required:after{margin-left:0;order:-9999}.form-horz .form-tip{width:100%}.form-horz .form-tip,.form-horz .input-control,.form-horz .input-group{flex:1 1 auto}.form .form-group-wrapper,.form-horz .form-group-wrapper{flex:1 1 auto;min-width:0;width:100%;z-index:1}.form .form-group-wrapper.flex-none,.form-horz .form-group-wrapper.flex-none{flex:none}.form fieldset>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.form fieldset{padding-bottom:1rem;padding-left:1rem}.form-grid fieldset>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.form legend{border-bottom-width:1px;display:flex;justify-content:flex-start;margin-left:-1rem;width:100%;--tw-border-opacity:1;border-bottom-color:rgba(var(--color-primary-100-rgb),var(--tw-border-opacity));width:calc(100% + 1rem)}.form-title{align-items:center;background-color:rgba(var(--color-primary-50-rgb),.5);display:flex;font-weight:700;height:1.75rem;padding-left:.75rem;padding-right:.75rem}:root{--input-control-fix-width-sm:2rem;--input-control-fix-width:4.375rem;--input-control-fix-width-lg:6.75rem}.input-control{position:relative;--input-control-prefix:8px;--input-control-suffix:8px}.input-control-prefix,.input-control-suffix{align-items:center;display:flex;height:100%;left:0;opacity:.5;padding-left:.5rem;padding-right:.5rem;position:absolute;top:0;white-space:nowrap;width:var(--input-control-prefix);z-index:1}.input-control-suffix{justify-content:flex-end;left:auto;right:0;width:var(--input-control-suffix)}.form-control:focus+.input-control-prefix,.form-control:focus+.input-control-suffix{opacity:1}.input-control>.form-control{padding-left:var(--input-control-prefix);padding-right:var(--input-control-suffix)}.input-control>select.form-control{background-position-x:calc(100% - var(--input-control-suffix) - 8px);padding-right:calc(var(--input-control-suffix) + 20px)}.has-prefix{--input-control-prefix:var(--input-control-fix-width)}.has-suffix{--input-control-suffix:var(--input-control-fix-width)}.has-prefix-sm{--input-control-prefix:var(--input-control-fix-width-sm)}.has-suffix-sm{--input-control-suffix:var(--input-control-fix-width-sm)}.has-prefix-lg{--input-control-prefix:var(--input-control-fix-width-lg)}.has-suffix-lg{--input-control-suffix:var(--input-control-fix-width-lg)}.has-prefix-icon{--input-control-prefix:32px}.has-suffix-icon{--input-control-suffix:32px}.input-control.has-prefix-icon{--input-control-prefix:32px}.input-control.has-suffix-icon{--input-control-suffix:32px}.input-control.has-prefix-icon>.input-control-prefix,.input-control.has-suffix-icon>.input-control-suffix{justify-content:center;padding:0}.input-control.size-sm>.form-control,.input-control.size-sm>.input-control-prefix,.input-control.size-sm>.input-control-suffix{font-size:.75rem;line-height:1rem}.input-control.size-lg>.form-control,.input-control.size-lg>.input-control-prefix,.input-control.size-lg>.input-control-suffix{font-size:1rem;line-height:1.5rem}:root{--label-bg:rgba(var(--color-canvas-rgb),.1);--label-border-color:var(--color-gray-300);--label-color:var(--color-gray-500);--label-radius:var(--radius)}.label{align-items:center;background-color:var(--label-bg);border-radius:var(--label-radius);color:var(--label-color);display:inline-flex;font-size:.75rem;height:1.25rem;justify-content:center;line-height:1rem;min-width:1.25rem;padding-left:.25rem;padding-right:.25rem;white-space:pre-line;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--label-border-color)}.label.size-lg{font-size:.8125rem;height:1.5rem;line-height:1.25rem;min-width:1.5rem;padding-left:.5rem;padding-right:.5rem}.label.size-sm{height:1rem;min-width:1rem}.label-dot{aspect-ratio:1/1;border-radius:var(--radius-full);height:.5rem;min-width:0;padding-left:0;padding-right:0}.caret,.caret-down,.caret-left,.caret-right,.caret-up{align-items:center;display:inline-flex;height:.75rem;justify-content:center;position:relative;width:.75rem}.caret-down:before,.caret-left:before,.caret-right:before,.caret-up:before,.caret:before{display:block;height:.35rem;transform-origin:center;width:.35rem;--tw-translate-y:-1px;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.caret-left:before{--tw-translate-x:0.125rem;--tw-translate-y:0px;--tw-rotate:135deg}.caret-left:before,.caret-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.caret-right:before{--tw-translate-x:-0.125rem;--tw-translate-y:0px;--tw-rotate:-45deg}.caret-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:focus>.caret,:hover>.caret{opacity:inherit}.disabled .caret,.readonly .caret{opacity:var(--caret-opacity,.5)}.listitem{align-items:center;border-radius:var(--radius);display:flex;flex-direction:row;flex-wrap:nowrap;gap:.5rem;padding:.25rem}.listitem.selected{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.listitem.active{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.item-actions,.item-avatar,.item-icon,.item-trailing,.item-trailing-icon{flex:none}.item-icon.icon-EMPTY{display:none}.item-subtitle{font-size:.75rem;line-height:1rem;opacity:.8}.item-content,.item-text{flex:1 1 auto;min-width:0}.item-leading,.item-trailing{align-items:center;display:flex;flex:none;gap:.5rem}.item-checkbox{margin-right:-.5rem}.item-content{align-items:center;display:flex;gap:.5rem}.multiline>.item-content{align-items:flex-start;flex-direction:column;gap:.25rem}.list{list-style-type:none;padding-left:0}.list-heading-inner .item-title{font-weight:700;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.list.is-nested-sub{padding-left:var(--list-indent)}.is-nested-collapsed{display:none}.nested-toggle-icon{align-items:center;border-radius:var(--radius);display:flex;height:1rem;justify-content:center;margin-right:-.25rem;width:1rem}.magnifier{display:inline-block;height:1em;position:relative;width:1em}.magnifier:after,.magnifier:before{border-radius:var(--radius-full);content:"";display:block;position:absolute}.magnifier:before{border:1px solid;height:.75em;width:.75em}.magnifier:after{height:1px;left:.55em;top:.7em;width:.5em;--tw-rotate:45deg;background-color:currentColor;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.search-box.compact.has-prefix-icon{--input-control-prefix:24px}.search-box.compact.has-suffix-icon{--input-control-suffix:24px}:root{--menu-bg:var(--color-canvas);--menu-active-bg:var(--color-primary-500);--menu-active-color:var(--color-canvas);--menu-selected-bg:var(--color-primary-50);--menu-selected-color:var(--color-primary-500);--menu-icon-opacity:.5;--menu-icon-margin:1.75rem;--menu-min-width:3rem;--menu-heading-color:var(--color-gray-500)}.menu{background:var(--menu-bg);max-width:var(--menu-max-width);min-width:var(--menu-min-width);padding:.5rem}.menu-wrapper{display:flex;flex-direction:column;min-height:0}.menu-wrapper>.menu{flex:1 1 auto;min-height:0;overflow:auto}.menu-item>.item-inner,.menu-item>a{align-items:center;border-radius:var(--radius);color:inherit;cursor:pointer;display:flex;gap:.5rem;justify-content:space-between;overflow:hidden;padding:.25rem .5rem;position:relative;text-overflow:ellipsis;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1);white-space:nowrap}.menu-item>.selected{background:var(--menu-selected-bg);color:var(--menu-selected-color)}.menu-item>.active,.menu-item>a.hover,.menu-item>a:hover{background:var(--menu-active-bg);color:var(--menu-active-color)}.menu-item.disabled>a:hover,.menu-item>a.disabled:hover{background-color:inherit;color:inherit}.menu-item .item-title{flex:1 1 auto;min-width:0;overflow:hidden;text-overflow:clip;white-space:nowrap}.menu>.divider{margin:.25rem}.menu-heading{align-items:center;color:var(--menu-heading-color);display:flex;font-size:.75rem;font-weight:700;height:2rem;line-height:1rem;padding-left:.25rem;padding-right:.25rem}.has-icons>.menu-item>a>.item-icon{align-items:center;display:flex;height:1rem;justify-content:center;opacity:var(--menu-icon-opacity);width:1rem}.menu-nested{--menu-indent:10px}.menu-nested .menu{background-color:transparent;margin-bottom:-.5rem;margin-left:var(--menu-indent);margin-top:-.5rem;padding-right:0}.menu-nested .menu-item>.item-inner{padding-left:0}.menu-nested .search-menu-footer,.menu-nested .search-menu-header{margin-bottom:.25rem;margin-left:var(--menu-indent);margin-top:-.125rem;padding-right:1px}.menu.compact .menu-item>a{padding-bottom:.125rem;padding-top:.125rem}.menu.compact .menu-heading{height:1.75rem}.search-menu-header{padding:.5rem .5rem .125rem}.search-menu-footer{padding:.125rem .5rem .5rem}.search-menu .item.is-not-match,.search-menu-footer:empty,.search-menu-header:empty{display:none}.search-menu .item.is-not-match.has-match-child{display:list-item}.search-menu .item.is-not-match.has-match-child>.item-inner{opacity:.5;pointer-events:none}.search-menu.no-toggle-on-search .nested-toggle-icon{pointer-events:none}.search-menu .is-match-keys{font-weight:700;text-decoration-line:underline}.search-menu-no-match-hint{display:none;font-size:.75rem;line-height:1rem;padding:.5rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.no-match-child .search-menu-no-match-hint{display:block}.no-match-child>.menu{display:none}:root{--alert-bg:var(--color-surface)}.alert{align-items:center;background-color:var(--alert-bg);border-radius:var(--radius);display:flex;gap:.75rem;padding:.5rem .75rem}.alert-content{display:flex;flex:1 1 auto;flex-direction:column;gap:1rem}.alert-close{margin-bottom:-.375rem;margin-right:-.5rem;margin-top:-.375rem}.alert-link{color:inherit;font-weight:700}.alert-link:hover{color:inherit;text-decoration-line:underline}.alert-heading{font-weight:700;margin:0}.alert-text{flex:1 1 auto;white-space:pre-line}.alert-actions{align-items:center;display:flex;gap:.5rem}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.messagers{align-items:flex-end;bottom:0;display:flex;flex-direction:column;gap:.5rem;justify-content:flex-end;left:0;padding:1rem;pointer-events:none;position:fixed;right:0;top:0;z-index:1900}.messagers-top-left,.messagers-top-right{justify-content:flex-start}.messagers-bottom-left,.messagers-top-left{align-items:flex-start}.messagers-bottom,.messagers-center,.messagers-top{align-items:center}.messagers-top,.messagers-top-left,.messagers-top-right{justify-content:flex-start}.messagers-center{justify-content:center}.messager{background-color:rgba(var(--color-inverse-rgb),.8);pointer-events:auto;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);transition-duration:.3s}:root{--progress-radius:var(--radius);--progress-striped-size:40px;--progress-bg:var(--color-surface);--progress-bar-color:var(--color-primary-500)}.progress{background:var(--progress-bg);border-radius:var(--progress-radius);display:flex;height:1.25rem}.progress-bar{background:var(--progress-bar-color);height:100%;transition-duration:.5s;transition-property:width;transition-timing-function:cubic-bezier(.4,0,.2,1)}.progress-striped>.progress-bar{background-image:linear-gradient(45deg,rgba(var(--color-canvas-rgb),.15) 25%,transparent 25%,transparent 50%,rgba(var(--color-canvas-rgb),.15) 50%,rgba(var(--color-canvas-rgb),.15) 75%,transparent 75%,transparent);background-size:var(--progress-striped-size) var(--progress-striped-size)}.progress>.progress-bar:first-child{border-bottom-left-radius:inherit;border-top-left-radius:inherit}.progress>.progress-bar:last-child{border-bottom-right-radius:inherit;border-top-right-radius:inherit}.progress.active .progress-bar{animation:progress-bar-stripes 2s linear infinite}@keyframes progress-bar-stripes{0%{background-position:40px 0}to{background-position:0 0}}.scrollbar,:root{--scrollbar-size:10px;--scrollbar-opacity:.6;--scrollbar-bg:rgba(var(--color-inverse-rgb),.15);--scrollbar-inset:inset 0 0 0 1px rgba(var(--color-inverse-rgb),.05);--scrollbar-bar-bg:rgba(var(--color-inverse-rgb),.3);--scrollbar-hover-bg:rgba(var(--color-inverse-rgb),.4);--scrollbar-drag-bg:rgba(var(--color-inverse-rgb),.5);--scrollbar-radius:var(--radius-sm);--scrollbar-duration:.7s}::-webkit-scrollbar{height:var(--scrollbar-size);width:var(--scrollbar-size)}::-webkit-scrollbar-track{box-shadow:var(--scrollbar-shadow);-webkit-transition:background-color var(--scrollbar-duration);transition:background-color var(--scrollbar-duration)}::-webkit-scrollbar-track:hover,:hover::-webkit-scrollbar-track{background:var(--scrollbar-bg)}::-webkit-scrollbar-thumb{background:var(--scrollbar-bar-bg);border-radius:var(--scrollbar-radius);min-height:var(--scrollbar-size);-webkit-transition:var(--scrollbar-duration);transition:var(--scrollbar-duration);-webkit-transition-property:background-color;transition-property:background-color}::-webkit-scrollbar-thumb:hover{background:var(--scrollbar-hover-bg)}::-webkit-scrollbar-thumb:active{background:var(--scrollbar-drag-bg)}@-moz-document url-prefix(){.scrollbar-thin{scrollbar-width:thin}}.scrollbar-thin::-webkit-scrollbar{height:calc(var(--scrollbar-size)/2);width:calc(var(--scrollbar-size)/2)}.scrollbar-hover::-webkit-scrollbar,.scrollbar-hover::-webkit-scrollbar-thumb,.scrollbar-hover::-webkit-scrollbar-track{visibility:hidden}.scrollbar-hover:hover::-webkit-scrollbar,.scrollbar-hover:hover::-webkit-scrollbar-thumb,.scrollbar-hover:hover::-webkit-scrollbar-track{visibility:visible}@font-face{font-family:ZentaoIcon;font-style:normal;font-weight:400;src:url(./icons/ZentaoIcon.eot?v=1.70);src:url(./icons/ZentaoIcon.woff?v=1.70) format("woff"),url(./icons/ZentaoIcon.ttf?v=1.70) format("truetype"),url(./icons/ZentaoIcon.svg?v=1.70#regular) format("svg")}.icon,[class*=" icon-"],[class^=icon-]{display:inline-block;font-display:block;font-family:ZentaoIcon;font-size:14px;font-style:normal;font-variant:normal;font-weight:400;line-height:1;text-transform:none;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.icon:before{display:inline-block;min-width:14px;text-align:center}.icon-xs:before{font-size:.7em}.icon-sm:before{font-size:.8em}.icon-lg:before{font-size:1.25em;vertical-align:-10%}.icon-2x{font-size:28px}.icon-3x{font-size:42px}.icon-4x{font-size:56px}.icon-5x{font-size:70px}.icon-run{position:relative}.icon-run:before{opacity:.5}.icon-run:after{bottom:0;content:"\ea07";display:block;left:0;position:absolute;right:0;text-align:center;top:0}.icon-guihua:before{content:"\ea02"}.icon-memory:before{content:"\e9fd"}.icon-cpu:before{content:"\e9fe"}.icon-pause-pure:before{content:"\e9ff"}.icon-exclamation-pure:before{content:"\ea00"}.icon-zentao:before{content:"\e901"}.icon-zentao-alt:before{content:"\e900"}.icon-safe:before{content:"\ea06"}.icon-ai:before{content:"\e983"}.icon-kanban:before{content:"\e997"}.icon-college:before{content:"\e9c8"}.icon-home:before,.icon-menu-my:before{content:"\e97a"}.icon-program:before{content:"\e9aa"}.icon-lightbulb-alt:before,.icon-product:before{content:"\e98f"}.icon-project:before,.icon-rocket:before{content:"\e99c"}.icon-run:before{content:"\e9a9"}.icon-run-alt:before{content:"\ea07"}.icon-test:before{content:"\e956"}.icon-devops:before,.icon-infinite:before{content:"\e9a3"}.icon-doc:before,.icon-menu-doc:before{content:"\e99b"}.icon-statistic:before{content:"\e999"}.icon-group:before,.icon-menu-users:before,.icon-persons:before,.icon-team:before{content:"\e97e"}.icon-assets:before,.icon-diamond:before{content:"\e9ae"}.icon-flow:before{content:"\e994"}.icon-backend:before,.icon-cog-outline:before{content:"\ea05"}.icon-help:before{content:"\e968"}.icon-download:before,.icon-import:before{content:"\e904"}.icon-export:before{content:"\e905"}.icon-lightbulb:before{content:"\e91c"}.icon-close:before{content:"\e936"}.icon-check:before{content:"\e5ca"}.icon-minus:before{content:"\e926"}.icon-expand-alt:before{content:"\e6f1"}.icon-collapse-alt:before{content:"\e6f2"}.icon-fullscreen:before{content:"\e96b"}.icon-star-empty:before{content:"\e94a"}.icon-star:before{content:"\e94b"}.icon-exclamation-sign:before{content:"\e930"}.icon-info-sign:before{content:"\e9d5"}.icon-flag:before{content:"\e937"}.icon-check-circle:before{content:"\e92f"}.icon-check-sign:before{content:"\e938"}.icon-chart-pie:before{content:"\e95b"}.icon-history:before{content:"\e95f"}.icon-pencil:before{content:"\e254"}.icon-search:before{content:"\e928"}.icon-restart:before{content:"\e95e"}.icon-cog:before{content:"\e93b"}.icon-chart-line:before{content:"\e95c"}.icon-bar-chart:before,.icon-chart-bar:before{content:"\e95d"}.icon-exchange:before{content:"\e927"}.icon-severity:before{content:"\e973"}.icon-book:before{content:"\f02d"}.icon-treemap-alt:before{content:"\e971"}.icon-severity-solid:before{content:"\e902"}.icon-chat-line:before{content:"\e998"}.icon-stack:before{content:"\e943"}.icon-cube:before{content:"\e967"}.icon-minus-sign:before{content:"\e939"}.icon-bars-sign:before{content:"\e93a"}.icon-chat:before,.icon-message:before{content:"\e940"}.icon-more:before{content:"\e744"}.icon-certificate:before{content:"\f0a3"}.icon-bell:before{content:"\e7f5"}.icon-columns:before{content:"\f0db"}.icon-envelope-o:before{content:"\e92a"}.icon-unfold-all:before{content:"\e931"}.icon-fold-all:before{content:"\e932"}.icon-bars:before{content:"\e948"}.icon-cards-view:before{content:"\e949"}.icon-ellipsis-v:before{content:"\e5d4"}.icon-spinner-indicator:before{content:"\e982"}.icon-up-circle:before{content:"\e92b"}.icon-right-circle:before{content:"\e92c"}.icon-down-circle:before{content:"\e92d"}.icon-left-circle:before{content:"\e92e"}.icon-angle-double-right:before{content:"\f101"}.icon-angle-down:before{content:"\e313"}.icon-angle-left:before{content:"\e314"}.icon-angle-right:before{content:"\e315"}.icon-angle-top:before{content:"\e316"}.icon-first-page:before{content:"\e5dc"}.icon-last-page:before{content:"\e5dd"}.icon-caret-down:before{content:"\f0d7"}.icon-caret-up:before{content:"\f0d8"}.icon-caret-left:before{content:"\f0d9"}.icon-caret-right:before{content:"\f0da"}.icon-sort:before{content:"\f0dc"}.icon-sort-down:before{content:"\f0dd"}.icon-sort-up:before{content:"\f0de"}.icon-arrow-up:before{content:"\e923"}.icon-arrow-down:before{content:"\e924"}.icon-arrow-left:before{content:"\e952"}.icon-arrow-right:before{content:"\e93e"}.icon-chevron-left:before{content:"\e934"}.icon-chevron-right:before{content:"\e935"}.icon-chevron-double-up:before{content:"\e959"}.icon-chevron-double-down:before{content:"\e95a"}.icon-folder-account:before{content:"\e942"}.icon-folder-move:before{content:"\e960"}.icon-folder-plus:before{content:"\e961"}.icon-folder-upload:before{content:"\e962"}.icon-folder-star:before{content:"\e963"}.icon-folder-edit:before{content:"\e964"}.icon-folder-download:before{content:"\e965"}.icon-folder-outline:before{content:"\e966"}.icon-folder:before{content:"\e944"}.icon-folder-o:before{content:"\e945"}.icon-folder-open-o:before{content:"\e946"}.icon-folder-open:before{content:"\e947"}.icon-color:before{content:"\e93c"}.icon-paper-clip:before{content:"\e93d"}.icon-text:before{content:"\e929"}.icon-share:before{content:"\f064"}.icon-format-list-bulleted:before{content:"\e9a8"}.icon-format-bold:before{content:"\e953"}.icon-format-header-pound:before{content:"\e954"}.icon-format-italic:before{content:"\e955"}.icon-format-list-numbers:before{content:"\e969"}.icon-format-quote-close:before{content:"\e96a"}.icon-image:before{content:"\e96c"}.icon-table-large:before{content:"\e96d"}.icon-productplan:before{content:"\e9fc"}.icon-aiux:before{content:"\e99e"}.icon-qc:before{content:"\e986"}.icon-qc-q:before{content:"\e985"}.icon-qc-c:before{content:"\e987"}.icon-sonarqube:before{content:"\e9ba"}.icon-board:before{content:"\ea15"}.icon-market:before{content:"\ea01"}.icon-ztool:before{content:"\e9c1"}.icon-contacts:before{content:"\e9c3"}.icon-chats:before{content:"\e9c4"}.icon-ops:before{content:"\e903"}.icon-menu-backend:before{content:"\e993"}.icon-feedback:before{content:"\e991"}.icon-oa:before{content:"\e9a1"}.icon-more-circle:before{content:"\e988"}.icon-controls:before{content:"\e995"}.icon-account:before{content:"\e992"}.icon-about:before,.icon-info:before{content:"\e996"}.icon-exclamation:before{content:"\e9fa"}.icon-exit:before{content:"\e99a"}.icon-theme:before{content:"\e9a0"}.icon-globe:before,.icon-lang:before{content:"\f0ac"}.icon-template:before{content:"\e9fb"}.icon-seal:before{content:"\e9f8"}.icon-menu-arrow-left:before{content:"\e9f0"}.icon-menu-arrow-right:before{content:"\e9f1"}.icon-add-directory:before{content:"\e9ef"}.icon-design:before{content:"\e9ec"}.icon-download-alt:before{content:"\e9ea"}.icon-blame:before{content:"\e9e0"}.icon-draft-edit:before{content:"\e9dc"}.icon-sub-review-user:before{content:"\e9db"}.icon-sub-review:before{content:"\e9df"}.icon-ztf:before{content:"\e9dd"}.icon-save:before{content:"\e9d8"}.icon-list-box:before{content:"\e9b4"}.icon-usecase:before{content:"\e99d"}.icon-code:before{content:"\e990"}.icon-summary:before{content:"\e9ad"}.icon-more-alt:before{content:"\e9a7"}.icon-customer:before{content:"\e9d9"}.icon-alarm:before{content:"\ea16"}.icon-treeview:before{content:"\ea0d"}.icon-or:before{content:"\ea0b"}.icon-manager:before{content:"\ea0c"}.icon-target:before{content:"\ea0a"}.icon-ipd:before{content:"\e9f9"}.icon-wiki-lib:before{content:"\e9f5"}.icon-annex-lib:before{content:"\e9f6"}.icon-interface-lib:before{content:"\e9f7"}.icon-has-authority-pack:before{content:"\e9f3"}.icon-without-authority-pack:before{content:"\e9f4"}.icon-data-structure:before{content:"\e9f2"}.icon-waterfallplus:before{content:"\e9ed"}.icon-agileplus:before{content:"\e9ee"}.icon-horn:before{content:"\e9eb"}.icon-resume:before{content:"\e9e9"}.icon-mirror:before{content:"\e9e6"}.icon-remote:before{content:"\e9e7"}.icon-moon:before{content:"\e9e8"}.icon-ticket:before{content:"\e9e1"}.icon-gantt-alt:before{content:"\e9e2"}.icon-tree:before{content:"\e9c9"}.icon-list:before{content:"\e9cb"}.icon-gantt:before{content:"\e9cc"}.icon-group-view:before{content:"\e9cd"}.icon-inherit-space:before{content:"\e9c2"}.icon-card-archive:before{content:"\e9b8"}.icon-col-archive:before{content:"\e9b9"}.icon-col-add-right:before{content:"\e9bb"}.icon-col-add-left:before{content:"\e9bc"}.icon-col-split:before{content:"\e9bd"}.icon-waterfall:before{content:"\e9a4"}.icon-manual:before{content:"\e98d"}.icon-lane:before{content:"\e9b1"}.icon-mobile:before{content:"\ea18"}.icon-clear:before{content:"\ea19"}.icon-db:before{content:"\ea17"}.icon-unpinned:before{content:"\ea08"}.icon-pinned:before{content:"\ea09"}.icon-support-ticket:before{content:"\ea04"}.icon-snap-house:before{content:"\e9e3"}.icon-wrench:before{content:"\e9e4"}.icon-desktop:before{content:"\e9e5"}.icon-back-circle:before{content:"\e9da"}.icon-back:before{content:"\e9d3"}.icon-shield:before{content:"\e9ca"}.icon-meh:before{content:"\e9ce"}.icon-frown:before{content:"\e9cf"}.icon-smile:before{content:"\e9d0"}.icon-unlock-solid:before{content:"\e9d1"}.icon-lock-solid:before{content:"\e9d2"}.icon-ver:before{content:"\e9c6"}.icon-publish:before,.icon-send:before{content:"\e9c7"}.icon-tag:before{content:"\e9be"}.icon-tag-lock:before{content:"\e9bf"}.icon-code-fork:before{content:"\f126"}.icon-branch-lock:before{content:"\e9c0"}.icon-groups:before{content:"\e9af"}.icon-thumbs-up:before{content:"\f087"}.icon-thumbs-down:before{content:"\f088"}.icon-thumbs-up-solid:before{content:"\e9d6"}.icon-thumbs-down-solid:before{content:"\e9d7"}.icon-hash:before,.icon-version:before{content:"\e9ab"}.icon-p-square:before{content:"\e97b"}.icon-video-play:before{content:"\e97f"}.icon-plus-solid-circle:before{content:"\e974"}.icon-minuse-solid-circle:before{content:"\e9b6"}.icon-s:before{content:"\e975"}.icon-c:before{content:"\e976"}.icon-t:before{content:"\e977"}.icon-guide:before{content:"\e978"}.icon-todo:before{content:"\e979"}.icon-plus:before{content:"\e925"}.icon-side-left:before{content:"\e9b3"}.icon-side-right:before{content:"\e9b2"}.icon-fullscreen-exit:before{content:"\e972"}.icon-alert:before{content:"\e99f"}.icon-undo:before{content:"\e93f"}.icon-redo:before{content:"\e9d4"}.icon-swap:before{content:"\e9b0"}.icon-chat-solid:before{content:"\e9b5"}.icon-clock:before{content:"\e97c"}.icon-cost:before{content:"\e97d"}.icon-pencil-alt:before{content:"\e984"}.icon-size-height:before{content:"\e9c5"}.icon-upload-file:before{content:"\ea03"}.icon-file-log:before{content:"\e9de"}.icon-rich-text:before{content:"\e913"}.icon-markdown:before{content:"\e916"}.icon-excel:before{content:"\e933"}.icon-text-link:before{content:"\e94d"}.icon-ppt:before{content:"\e957"}.icon-word:before{content:"\e958"}.icon-doc-lib:before{content:"\e96f"}.icon-file-empty:before,.icon-file:before{content:"\f016"}.icon-file-text:before{content:"\f0f6"}.icon-file-alt:before{content:"\f15b"}.icon-file-text-alt:before{content:"\f15c"}.icon-file-pdf:before{content:"\f1c1"}.icon-file-word:before{content:"\f1c2"}.icon-file-excel:before{content:"\f1c3"}.icon-file-powerpoint:before{content:"\f1c4"}.icon-file-image:before{content:"\f1c5"}.icon-file-archive:before{content:"\f1c6"}.icon-file-audio:before{content:"\f1c7"}.icon-file-video:before{content:"\f1c8"}.icon-file-code:before{content:"\f1c9"}.icon-multi-input:before{content:"\ea1a"}.icon-cell-input:before{content:"\ea0e"}.icon-input:before{content:"\ea0f"}.icon-checkbox:before{content:"\ea10"}.icon-radio:before{content:"\ea11"}.icon-transition:before{content:"\ea12"}.icon-add-sub-chapter:before{content:"\ea13"}.icon-add-chapter:before{content:"\ea14"}.icon-menu-collapse:before{content:"\e980"}.icon-menu-expand:before{content:"\e981"}.icon-estimate:before{content:"\e9ac"}.icon-sprint:before{content:"\e9a2"}.icon-shield-check:before{content:"\e9a5"}.icon-ok:before{content:"\e9a6"}.icon-printer:before{content:"\e906"}.icon-bullhorn:before{content:"\e910"}.icon-person:before{content:"\e941"}.icon-fields:before{content:"\e989"}.icon-trigger:before{content:"\e98a"}.icon-layout:before{content:"\e98b"}.icon-audit:before{content:"\e98c"}.icon-ban-circle:before,.icon-cancel:before{content:"\e951"}.icon-eye:before{content:"\e94e"}.icon-eye-off:before{content:"\e96e"}.icon-unlock:before{content:"\e94f"}.icon-lock:before,.icon-private:before{content:"\e950"}.icon-move:before{content:"\e94c"}.icon-hand-right:before{content:"\e907"}.icon-checked:before{content:"\e908"}.icon-off:before{content:"\e909"}.icon-play:before,.icon-start:before{content:"\e90a"}.icon-time:before{content:"\e90b"}.icon-edit:before{content:"\e90c"}.icon-trash:before{content:"\e90d"}.icon-link:before{content:"\e90e"}.icon-unlink:before{content:"\e90f"}.icon-bug:before{content:"\e911"}.icon-list-alt:before{content:"\e912"}.icon-alter:before,.icon-change:before{content:"\e970"}.icon-glasses:before,.icon-review:before{content:"\e914"}.icon-sitemap:before,.icon-testcase:before{content:"\e915"}.icon-pluses:before{content:"\e917"}.icon-report-list:before{content:"\e918"}.icon-active:before,.icon-magic:before{content:"\e919"}.icon-treemap:before{content:"\e91a"}.icon-confirm:before{content:"\e91b"}.icon-split:before{content:"\e98e"}.icon-calendar:before,.icon-delay:before{content:"\e91d"}.icon-pause:before{content:"\e91e"}.icon-ban:before{content:"\e91f"}.icon-plus-bold:before{content:"\e920"}.icon-copy:before{content:"\e921"}.icon-refresh:before{content:"\e922"}.icon-diff:before{content:"\e9b7"}.status-active,.status-asked,.status-normal,.status-unconfirmed,.status-wait{color:var(--color-status-normal,#313c52)}.status-active.status-issue,.status-checking,.status-commenting,.status-confirmed,.status-doing{color:#ff6f42}.status-blocked,.status-hangup,.status-pause,.status-suspended{color:#b89664}.status-clarify,.status-draft{color:#8166ee}.status-noreview,.status-reviewing,.status-wait.status-testcase{color:#18a6fd}.status-active.status-risk,.status-changed,.status-changing,.status-fail{color:#fb2b2b}.status-checked,.status-done,.status-pass,.status-replied,.status-resolved,.status-success{color:#0dbb7d}.status-cancel,.status-canceled,.status-investigate{color:var(--color-status-cancel,#838a9d)}.status-closed,.status-testtask.status-done{color:var(--color-status-closed,#9ea3b0)}.dark{--color-status-normal:#eff1f3;--color-status-cancel:#9ea3b0;--color-status-closed:#838a9d}@media (prefers-color-scheme:dark){.dark-auto{--color-status-normal:#eff1f3;--color-status-cancel:#9ea3b0;--color-status-closed:#838a9d}}.pri,[class*=" pri-"],[class^=pri-]{border-color:currentColor;border-radius:var(--radius-full);border-width:1px;display:inline-block;font-size:.75rem;height:1rem;line-height:1rem;line-height:14px;max-width:54px;min-width:16px;overflow:hidden;padding-left:.125rem;padding-right:.125rem;text-align:center;white-space:nowrap;--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.pri-1{color:rgb(255 73 18/var(--tw-text-opacity))}.pri-1,.pri-2{--tw-text-opacity:1}.pri-2{color:rgba(var(--color-warning-600-rgb),var(--tw-text-opacity))}.pri-3{color:rgb(59 130 246/var(--tw-text-opacity))}.pri-3,.pri-4{--tw-text-opacity:1}.pri-4{color:rgb(149 211 224/var(--tw-text-opacity))}.severity{display:inline-block;font-size:.75rem;height:1rem;line-height:1rem;line-height:14px;max-width:54px;min-width:16px;overflow:hidden;padding-left:.125rem;padding-right:.125rem;position:relative;text-align:center;white-space:nowrap;--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.severity:before{background-color:currentColor;background-repeat:no-repeat;height:100%;left:0;position:absolute;top:0;width:100%;z-index:0;--tw-content:attr(data-severity);content:var(--tw-content);-webkit-mask:url('data:image/svg+xml;charset=utf-8,');mask:url('data:image/svg+xml;charset=utf-8,');-webkit-mask-size:100% 100%;mask-size:100% 100%}.severity:after,.severity:before{display:inline-block}.severity:after{--tw-scale-x:.75;--tw-scale-y:.75;content:attr(data-severity);line-height:20px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.severity[data-severity="1"]{--tw-text-opacity:1;color:rgb(185 28 28/var(--tw-text-opacity))}.severity[data-severity="2"]{--tw-text-opacity:1;color:rgb(249 115 22/var(--tw-text-opacity))}.severity[data-severity="3"]{--tw-text-opacity:1;color:rgb(250 174 26/var(--tw-text-opacity))}.severity[data-severity="4"]{--tw-text-opacity:1;color:rgb(184 150 100/var(--tw-text-opacity))}.severity[data-severity="5"]{--tw-text-opacity:1;color:rgb(158 163 176/var(--tw-text-opacity))}.severity-label{background-color:transparent}.severity-label:after,.severity-label:before{--tw-content:none;content:var(--tw-content)}.risk-high{color:rgb(220 38 38/var(--tw-text-opacity))}.risk-high,.risk-middle{--tw-text-opacity:1}.risk-middle{color:rgb(234 179 8/var(--tw-text-opacity))}.label.label-id{border-radius:var(--radius-full);flex:none;--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-300-rgb),var(--tw-ring-opacity));--label-bg:rgba(var(--color-canvas-rgb),.1)}.nav-feature{--nav-active-bg:var(--color-primary-100);--nav-active-color:var(--color-fore)}.nav-feature .nav-checkbox>.checkbox,.nav-feature .nav-checkbox>.checkbox-primary,.nav-feature .nav-item>a{align-items:center;border-radius:var(--radius);height:2rem;padding-left:.625rem;padding-right:.625rem}.nav-feature .nav-item>a>.icon{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.sortable-list .listitem{cursor:move;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-left:.5rem;padding-right:.5rem}.sortable-list .sortable-ghost>.listitem{--tw-bg-opacity:1;background-color:rgba(var(--color-warning-50-rgb),var(--tw-bg-opacity))}.sortable-empty-shadow{height:1px!important;left:0!important;opacity:0!important;pointer-events:none!important;position:absolute!important;top:0!important;width:1px!important}:root{--avatar-radius:12.5%;--avatar-bg:var(--color-surface)}.avatar{align-items:center;aspect-ratio:1/1;background:var(--avatar-bg);border-radius:var(--avatar-radius);display:inline-flex;justify-content:center;overflow:hidden;width:2rem}.avatar>img{height:100%;margin:0;-o-object-fit:cover;object-fit:cover;width:100%}.avatar.size-xs{width:1.25rem}.avatar.size-sm,.avatar.size-xs{font-size:.75rem;line-height:1rem}.avatar.size-sm{width:1.5rem}.avatar.size-lg{font-size:1.5rem;line-height:2rem;width:3rem}.avatar.size-xl{font-size:2.25rem;line-height:2.5rem;width:5rem}.avatar-group{display:flex;gap:.625rem}.avatar-group>.avatar{box-shadow:0 0 0 1px var(--color-canvas)}.avatar-group>*+*{margin-left:-1rem}.avatar-group.size-xs>*+*{margin-left:-.75rem}.avatar-group.size-sm>*+*{margin-left:-.875rem}.avatar-group.size-lg>*+*{margin-left:-1.25rem}.avatar-group.size-xl>*+*{margin-left:-1.5rem}.btn-group{display:flex;gap:1px}.btn-group>.btn.active{z-index:1}.btn-group>.btn:focus-within,.btn-group>.btn:hover{z-index:2}.btn-group>.btn.disabled,.btn-group>.btn:disabled{z-index:0}.btn-group>.btn:not(:first-child){border-bottom-left-radius:var(--radius-none);border-left-color:rgba(var(--color-canvas-rgb),.2);border-left-width:1px;border-top-left-radius:var(--radius-none)}.btn-group>.btn:not(:first-child):before{left:-1px}.btn-group>.btn:not(:last-child){border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none)}.color-picker-heading{align-items:center;font-weight:700;justify-content:space-between;margin-bottom:-.25rem;padding:.5rem}.color-picker-heading,.color-picker-row{display:flex;flex-direction:row}.color-picker-row{flex-wrap:wrap;gap:.5rem;padding:.75rem}.color-picker-item{align-items:center;border-radius:var(--radius-full);display:flex;height:1.25rem;justify-content:center;padding-left:.125rem;padding-right:.125rem;width:1.25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.pick-container{left:0;pointer-events:none;position:absolute;top:0;z-index:1600}.pick-pop{display:flex;flex-direction:column;opacity:0;pointer-events:auto;position:absolute;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);z-index:1200}.pick-pop.in{opacity:1}.date-picker-menu{--menu-bg:none}.date-picker-menu .mini-calendar{margin-top:-.75rem}.date-pick-menu-month,.date-pick-menu-years{display:flex;flex-direction:row;flex-wrap:wrap;gap:1px;max-height:237px;padding-bottom:.5rem;padding-left:.5rem;padding-right:.5rem}.date-pick-menu-years>.btn{width:2.5rem}.date-pick-menu-years>.btn.is-current{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.date-pick-menu-month>.btn.active,.date-pick-menu-years>.btn.active{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.date-pick-menu-month>.btn{width:3rem}.date-picker-menu-footer{border-top-width:1px;display:flex;flex-direction:row;padding:.25rem}.date-picker-menu-footer>.toolbar{flex:1 1 auto;justify-content:center}.date-picker-menu>.menu{border-right-width:1px}.date-picker-menu .menu-item{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.time-picker-menu{max-height:inherit}.time-picker-menu .menu-item>a{justify-content:center;padding-left:0;padding-right:0;text-align:center}.datetime-picker-menu{max-height:inherit}.mini-calendar{padding:.5rem}.mini-calendar>.row>.col{align-items:center;justify-content:center;width:14.2857%}.mini-calendar-day{height:2rem}.mini-calendar-day.disabled{pointer-events:none;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-200-rgb),var(--tw-bg-opacity));opacity:.5}.mini-calendar-day>.btn{width:2rem}.mini-calendar-day.is-weekend>.btn{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.mini-calendar-day.active>.btn,.mini-calendar-day.is-today>.btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.mini-calendar-day.selected>.btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.mini-calendar-day.is-out-month{opacity:.5}.i-time{border-color:currentColor;border-radius:50%;border-width:.08em;display:inline-block;height:1em;position:relative;width:1em}.i-time:after{border-color:currentColor;border-width:0 0 .08em .08em;height:.385em;left:.3846em;position:absolute;top:.08em;width:.385em;--tw-content:"";content:var(--tw-content)}.chevron-down,.chevron-left,.chevron-right,.chevron-up{align-items:center;display:inline-flex;height:1em;justify-content:center;position:relative;width:1em}.chevron-down:before,.chevron-left:before,.chevron-right:before,.chevron-up:before{display:block;height:.6923077em;transform-origin:center;width:.6923077em;--tw-translate-y:-0.125rem;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.chevron-left:before{--tw-translate-y:0px;--tw-translate-x:0.125rem;--tw-rotate:135deg}.chevron-left:before,.chevron-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-right:before{--tw-translate-y:0px;--tw-translate-x:-0.125rem;--tw-rotate:-45deg}.chevron-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.i-calendar{border-radius:2px;display:inline-block;height:.79em;margin-top:.16em;position:relative;width:1em}.i-calendar,.i-calendar:after,.i-calendar:before{border-color:currentColor;border-width:.08em}.i-calendar:after,.i-calendar:before{position:absolute;--tw-content:"";content:var(--tw-content)}.i-calendar:before{border-bottom-width:0;left:.15em;top:.307em;width:.6em}.i-calendar:after{border-bottom-width:0;border-top-width:0;height:.3077em;left:.17em;top:-.154em;width:.538em}:root{--modal-radius:var(--radius-lg);--modal-bg:rgba(var(--color-inverse-rgb),.4);--modal-sm:37.5rem;--modal-base:50rem;--modal-lg:75rem;--modal-xl:90rem}.modal{align-items:center;background-color:var(--modal-bg);bottom:0;display:none;justify-content:center;left:0;overflow:hidden;position:fixed;right:0;top:0;z-index:1500}.modal.load-indicator:before{background-color:transparent;transition-property:none}.modal.loading:after{--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.modal.loading .modal-dialog{opacity:0!important}.modal.show{display:flex}.modal-no-backdrop{background-color:transparent;pointer-events:none}.modal-hide{opacity:0!important}.modal-dialog{background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));pointer-events:auto;position:relative;--tw-bg-opacity:0.9;--tw-shadow:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--tw-shadow-colored:0 10px 50px -10px var(--tw-shadow-color),0 8px 20px -10px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);border-radius:var(--modal-radius);width:var(--modal-base)}.modal-content,.modal-dialog{max-height:100vh}.modal-content{display:flex;flex-direction:column;height:100%}.loading>.modal-dialog>.modal-content{opacity:0;visibility:hidden}.modal-dialog.loading{background-color:transparent}.modal-dialog.loading>.modal-content{display:none}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.modal-header{align-items:center;display:flex;flex:none;flex-wrap:nowrap;gap:1rem;padding:1rem 1.25rem;position:relative}.modal-title{flex:1 1 auto;font-size:1rem;font-weight:700;line-height:1.5rem}.modal-actions{position:absolute;right:.75rem;top:.75rem;z-index:15}.modal-body{flex:1 1 auto;overflow:auto;padding:1rem 1.25rem}.modal-footer{align-items:center;display:flex;flex:none;gap:.75rem;padding:1.25rem}.modal-dialog.size-full,.modal-dialog[data-size=full]{border-radius:var(--radius-none);height:100vh;width:100vw}.modal-dialog.size-sm,.modal-dialog[data-size=sm]{width:var(--modal-sm)}.modal-dialog.size-lg,.modal-dialog[data-size=lg]{width:var(--modal-lg)}.modal-dialog.size-xl,.modal-dialog[data-size=xl]{width:var(--modal-xl)}.modal-iframe{flex:1 1 auto;width:100%}.modal-trans{opacity:0;transition-duration:.2s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.modal-trans.in{opacity:1}.modal-trans>.modal-dialog{transition-property:transform,opacity;--tw-scale-x:.95;--tw-scale-y:.95;opacity:0;transition-duration:.3s}.modal-trans.in>.modal-dialog,.modal-trans>.modal-dialog{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.modal-trans.in>.modal-dialog{--tw-scale-x:1;--tw-scale-y:1;opacity:1}.modal-alert .modal-footer{justify-content:flex-end}.modal-alert .modal-header{margin-bottom:-1rem}.modal-alert .modal-body{overflow-wrap:break-word;white-space:pre-line}.modal-alert .modal-actions+.modal-body{padding-right:3rem}.modal-alert .modal-header+.modal-actions+.modal-body{padding-right:1.25rem}.file-selector{gap:.5rem;width:100%}.file-selector,.file-selector-box{display:flex;flex-direction:column}.file-selector-box{border-style:dashed;border-width:1px;gap:0;height:auto;justify-content:center;position:relative;--tw-border-opacity:1;background-color:rgba(var(--color-primary-50-rgb),.3);border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));padding:.5rem .75rem;--tw-ring-color:transparent;--state-color:rgba(var(--color-primary-500-rgb),.05)}.file-selector-box .text{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.is-dragging .file-selector-box{border-style:solid}.file-selector-btn{align-items:center;display:flex;gap:.5rem;position:relative}.is-dragging .file-selector-btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.file-selector-input{-webkit-appearance:none;-moz-appearance:none;appearance:none;bottom:0;cursor:pointer;left:0;opacity:.1;position:absolute;right:0;top:0}.file-selector-tip{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.file-selector.is-mode-button{flex-direction:column-reverse}.file-selector-list.is-empty{display:none}.file-selector-item .item-avatar{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.file-selector-item .item-subtitle{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.file-selector-item .item-content{flex:none;margin-right:.25rem;max-width:100%}.file-selector-item>.listitem:hover{background-color:rgba(var(--color-gray-500-rgb),.05)}.file-selector-item.is-renaming .item-avatar+.item-content{max-width:calc(100% - 32px)}.file-selector-rename-text{max-width:100%;min-width:100px;position:relative}.file-selector-rename-text>div{overflow:hidden;pointer-events:none;visibility:hidden;white-space:nowrap}.file-selector-rename-input{bottom:0;left:0;position:absolute;right:0;top:0}.file-selector-grid{align-items:flex-start;border-color:transparent;border-radius:var(--radius);border-width:1px;display:flex;flex-direction:row;flex-wrap:wrap;gap:var(--file-selector-grid-gap);--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity));padding:.5rem}.file-selector-grid-item{height:var(--file-selector-grid-height)}.file-selector-grid-btn,.file-selector-grid-item{width:var(--file-selector-grid-width)}.file-selector-grid-btn{aspect-ratio:1/1;border-style:dashed;border-width:1px;display:flex;flex-direction:column;gap:0;height:auto;justify-content:center;--tw-border-opacity:1;background-color:rgba(var(--color-primary-50-rgb),.3);border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));padding:.5rem;--tw-ring-color:transparent;--state-color:rgba(var(--color-primary-500-rgb),.05)}.file-selector-grid-btn .text{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.file-selector-grid-item .listitem{flex-direction:column;height:100%;padding:0;position:relative;width:100%}.file-selector-grid-item .item-avatar{border-radius:var(--radius);border-width:1px;width:100%;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.file-selector-grid-item .item-avatar.has-icon>.icon{font-size:calc(var(--file-selector-grid-width)/2)}.file-selector-grid-item .item-content,.file-selector-grid-item .toolbar{aspect-ratio:1/1;left:0;position:absolute;right:0;top:0;width:100%}.file-selector-grid-item .item-title{bottom:-1.25rem;font-size:.75rem;left:0;line-height:1rem;overflow:hidden;position:absolute;right:1.5rem;white-space:nowrap}.file-selector-grid-item .item-subtitle{border-radius:var(--radius-full);bottom:.25rem;left:.25rem;position:absolute;--tw-bg-opacity:1;background-color:rgba(var(--color-fore-rgb),var(--tw-bg-opacity));font-size:.75rem;line-height:1rem;padding-left:.25rem;padding-right:.25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.file-selector-grid-item:hover .item-subtitle{opacity:1}.file-selector-grid-item .toolbar .btn[data-remove-file]{background-color:rgba(var(--color-inverse-rgb),.5);padding:.375rem;position:absolute;right:1px;top:1px;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.file-selector-grid-item .toolbar .btn[data-rename-file]{bottom:-1.5rem;padding:0;position:absolute;right:0}.file-selector-grid .file-selector-rename{bottom:0;height:1.5rem;position:absolute;top:auto}.file-selector-grid .file-selector-rename-text{width:100%}.is-dragging .file-selector-grid{border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}:root{--nav-radius:var(--radius);--nav-active-color:var(--color-primary-500);--nav-active-bg:var(--color-inherit);--nav-heading-color:var(--color-gray-500);--nav-gap:0.25rem;--nav-item-color:inherit;--nav-item-bg:transparent;--nav-item-padding:1rem;--nav-item-height:2rem;--nav-item-gap:0.75rem;--nav-divider-height:calc(var(--nav-item-height)/2);--nav-divider-margin:0.5rem}.nav{list-style-type:none;padding-left:0}.nav,.nav-item{align-items:center;display:flex;position:relative}.nav-item{gap:var(--nav-item-gap)}.nav-item>a{align-items:center;background-color:var(--nav-item-bg);color:var(--nav-item-color);cursor:pointer;display:flex;gap:var(--nav-gap);height:var(--nav-item-height);justify-content:center;padding-left:var(--nav-item-padding);padding-right:var(--nav-item-padding)}.nav-item>a>.text{white-space:nowrap}.nav-item>.active{font-weight:700;--nav-item-color:var(--nav-active-color);--nav-item-bg:var(--nav-active-bg)}.nav-item>.selected{--nav-item-color:var(--nav-selected-color);--nav-item-bg:var(--nav-selected-bg)}.nav-item>.disabled{--nav-item-color:var(--nav-disabled-color);--nav-item-bg:var(--nav-disabled-bg)}.nav-item>.disabled>*{opacity:var(--opacity-disabled)}.nav-divider,.nav>.divider{align-self:center;height:var(--nav-divider-height);margin-left:var(--nav-divider-margin);margin-right:var(--nav-divider-margin)}.nav-heading{align-items:center;color:var(--nav-heading-color);display:flex;font-weight:700;gap:.25rem;height:2rem;justify-content:center;padding-left:1rem;padding-right:1rem}.nav-space{flex:1 1 auto;width:1rem}.nav-compact{--nav-gap:0.25rem;--nav-item-gap:0.5rem;--nav-item-height:1.75rem;--nav-item-padding:0.5rem;--nav-divider-margin:0.25rem}.nav-primary>.nav-item{position:relative}.nav-primary>.nav-item:hover{z-index:10}.nav-primary>.nav-item+.nav-item{margin-left:-1px}.nav-primary>.nav-item>a{border-radius:var(--radius-none);border-width:1px}.nav-primary>.nav-item:first-child>a,.nav-primary>.nav-item:has(.nav-heading)+.nav-item>a{border-bottom-left-radius:var(--nav-radius);border-top-left-radius:var(--nav-radius)}.nav-primary>.nav-item:last-child>a{border-bottom-right-radius:var(--nav-radius);border-top-right-radius:var(--nav-radius)}.nav-primary>.nav-item>.active{--tw-text-opacity:1;background:var(--nav-active-color);border-color:var(--nav-active-color);color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.nav-primary>.nav-divider{display:none}.nav-secondary>.nav-item>a{border-radius:var(--radius-none);position:relative}.nav-secondary>.nav-item>a:after{bottom:-2px;display:block;height:2px;left:0;position:absolute;right:0;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));--tw-content:"";content:var(--tw-content)}.nav-secondary>.nav-item>.active:after{background-color:currentColor}.nav-secondary>.nav-divider{margin:0 0 0 -1px}.nav-tabs>.nav-item>a{border-bottom-left-radius:var(--radius-none);border-bottom-right-radius:var(--radius-none);position:relative}.nav-tabs>.nav-item>a:after{border-color:transparent;border-width:1px;bottom:-1px;display:block;left:-1px;pointer-events:none;position:absolute;right:-1px;top:-1px;--tw-border-opacity:1;border-bottom-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-content:"";border-top-left-radius:inherit;border-top-right-radius:inherit;content:var(--tw-content)}.nav-tabs>.nav-item>.active:after{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-bottom-color:transparent}.nav-tabs>.nav-divider{margin:0 0 0 -1px}.nav-pills>.nav-item>a{border-radius:var(--radius-full)}.nav-pills>.nav-item>.active{--tw-text-opacity:1;background:var(--nav-active-color);border-color:var(--nav-active-color);color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.nav-steps{--nav-item-bg:var(--color-canvas);--nav-active-bg:var(--color-primary-500);--nav-active-color:var(--color-canvas);--nav-selected-bg:var(--color-secondary-500);--nav-selected-color:var(--color-canvas)}.nav-steps>.nav-item+.nav-item>a{padding-left:calc(var(--nav-item-padding) + var(--nav-item-height)/3)}.nav-steps>.nav-item>a:after,.nav-steps>.nav-item>a:before{border-style:solid;height:0;left:100%;position:absolute;width:0;z-index:2;--tw-content:"";border-color:transparent;border-left-color:var(--nav-item-bg,var(--color-canvas));border-width:calc(var(--nav-item-height)/2);border-left-width:calc(var(--nav-item-height)/3);border-right-width:0;content:var(--tw-content)}.nav-steps>.nav-item>a:before{background-color:transparent!important;border-left-color:var(--color-border);bottom:auto;left:calc(100% + 5.5px);opacity:1!important;right:auto;top:.4rem;transform:none;z-index:1;--nav-item-height:1.2rem}.nav-steps>.nav-item:has(+.nav-item>.active)>.selected:before,.nav-steps>.nav-item:has(+.nav-item>.active,+.nav-item>.selected)>a:not(.active,.selected):before,.nav-steps>.nav-item:has(+.nav-item>.selected)>.active:before,.nav-steps>.nav-item:last-child>a:after,.nav-steps>.nav-item:last-child>a:before{display:none}.nav-steps>.nav-item>a:hover{--nav-item-bg:var(--color-gray-100)}.nav-steps>.nav-item>.active:hover{--nav-item-bg:var(--color-primary-600)}.nav-steps>.nav-item>.selected:hover{--nav-item-bg:var(--color-secondary-600)}.nav-stacked{flex-direction:column}.nav-stacked>.nav-item{width:100%}.nav-stacked>.nav-heading,.nav-stacked>.nav-item>a{justify-content:flex-start;width:100%}.nav-stacked>.nav-divider{height:1px;margin:.5rem 0;width:100%}.nav-primary.nav-stacked>.nav-item>a{height:2.5rem}.nav-primary.nav-stacked>.nav-item+.nav-item{margin-left:0;margin-top:-1px}.nav-primary.nav-stacked>.nav-item:first-child>a{border-bottom-left-radius:0;border-top-left-radius:var(--nav-radius);border-top-right-radius:var(--nav-radius)}.nav-primary.nav-stacked>.nav-item:last-child>a{border-bottom-left-radius:var(--nav-radius);border-bottom-right-radius:var(--nav-radius);border-top-right-radius:0}.nav-secondary.nav-stacked>.nav-item>a:after{bottom:0;height:100%;left:auto;right:0;top:0;width:2px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity))}.nav-secondary.nav-stacked>.nav-item>.active:after{background-color:currentColor}.nav-secondary.nav-stacked>.nav-divider{margin:0}.nav-tabs.nav-stacked>.nav-item>a{border-bottom-left-radius:var(--nav-radius);border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none);position:relative}.nav-tabs.nav-stacked>.nav-item>a:after{--tw-border-opacity:1;border-bottom-color:transparent;border-bottom-left-radius:inherit;border-right-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-top-left-radius:inherit}.nav-tabs.nav-stacked>.nav-item>a.active:after{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-right-color:transparent}.nav-tabs.nav-stacked>.nav-divider{margin:0}.nav-pills.nav-stacked>.nav-item+.nav-item{margin-top:.25rem}.nav-justified>.nav-item:not(.flex-none,.nav-divider){flex:1 1 auto}.nav-justified>.nav-item>a{width:100%}.arrow,.arrow:before{background:inherit;height:calc(var(--arrow-size)*1.4142);position:absolute;width:calc(var(--arrow-size)*1.4142)}.arrow{visibility:hidden;--arrow-size:5px}.arrow:before{border:inherit;content:"";visibility:visible;--tw-rotate:45deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.arrow-top,.arrow-up{border-bottom:inherit;border-right:inherit;border-width:1px 0 0 1px;top:calc(1px - var(--arrow-size))}.white>.arrow-top,.white>.arrow-up{top:calc(0px - var(--arrow-size))}.arrow-bottom,.arrow-down{border-left:inherit;border-top:inherit;border-width:0 1px 1px 0;bottom:calc(1px - var(--arrow-size))}.white>.arrow-bottom,.white>.arrow-down{bottom:calc(0px - var(--arrow-size))}.arrow-left{border-right:inherit;border-top:inherit;border-width:0 0 1px 1px;left:calc(1px - var(--arrow-size))}.white>.arrow-left{left:calc(0px - var(--arrow-size))}.arrow-right{border-bottom:inherit;border-left:inherit;border-width:1px 1px 0 0;right:calc(1px - var(--arrow-size))}.white>.arrow-right{right:calc(0px - var(--arrow-size))}.popover{display:none;left:0;position:absolute;top:0;width:-moz-max-content;width:max-content}.popover.show{display:block}.popover-heading{align-items:center;border-top-left-radius:inherit;border-top-right-radius:inherit;display:flex;gap:1rem;height:2.5rem;justify-content:space-between;position:relative;z-index:1;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:.75rem;padding-right:.5rem}.popover-title{flex:1 1 auto;font-weight:700}.popover-content{padding:.75rem;position:relative;z-index:1}.popover-arrow{z-index:0}.has-heading>.popover-arrow.arrow-top,.has-heading>.popover-arrow.arrow-up{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.popover>.btn-close{position:absolute;right:.5rem;top:.625rem;z-index:2}.btn-close+.popover-content{padding-right:3rem}.btn.with-popover-show{--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.with-popover-show[data-pop-placement=top]>.caret{--tw-rotate:180deg}.with-popover-show[data-pop-placement=left]>.caret,.with-popover-show[data-pop-placement=top]>.caret{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.with-popover-show[data-pop-placement=left]>.caret{--tw-rotate:90deg}.with-popover-show[data-pop-placement=right]>.caret{--tw-rotate:-90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.pager{align-items:center;display:flex;gap:.25rem;white-space:nowrap}.menu.pager-size-menu{display:grid!important;grid-template-columns:repeat(3,minmax(0,1fr));text-align:center}.menu.pager-size-menu>.menu-item>a{margin:.125rem}.pager .pager-goto-group>.form-control{width:3rem}.pager .pager-goto-group>.input-group-addon{border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-300-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.pager>.pager-nav.active{--tw-text-opacity:1;box-shadow:0 0 0 1px var(--color-primary-500);color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.panel{border-radius:var(--radius);overflow:hidden;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05}.panel-heading{background-color:var(--panel-heading-bg);flex-wrap:nowrap;gap:1rem;justify-content:space-between;padding:.5rem 1rem}.panel-heading,.panel-title{align-items:center;display:flex}.panel-title{font-weight:700;gap:.5rem;margin:0}.panel-actions{align-items:center;display:flex;margin-right:-.5rem}.panel-body{padding:.75rem 1rem}.panel-footer{align-items:center;background-color:var(--panel-footer-bg);display:flex;gap:.5rem;padding:.5rem 1rem}.size-sm .panel-body,.size-sm .panel-footer,.size-sm .panel-heading{padding:.375rem .75rem}.size-lg .panel-body,.size-lg .panel-footer,.size-lg .panel-heading{padding:1rem 1.25rem}.picker{position:relative}.picker-select{align-items:center;gap:.25rem;justify-content:space-between}.picker-select,.picker-select.form-control{display:flex}.picker-select-placeholder{flex:1 1 auto;--tw-text-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-text-opacity))}.picker-select-multi .picker-select-placeholder{padding-left:.25rem;padding-right:.25rem}.picker-single-selection{flex:1 1 auto;min-width:0;overflow:hidden;white-space:nowrap}.picker-deselect-btn{border-radius:var(--radius-full);padding:.25rem}.picker-deselect-btn:not(:hover){opacity:.7}.picker-select-multi.form-control{height:auto;min-height:32px;padding-left:.25rem}.picker-multi-selections{display:flex;flex-wrap:wrap;gap:.25rem;min-width:0}.picker-multi-selection{align-items:center;border-radius:var(--radius-full);border-width:1px;display:flex;max-width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:.5rem}.readonly .picker-multi-selection{padding-right:.5rem}.picker-multi-selection>.text{max-width:180px;min-width:0;overflow:clip;white-space:nowrap}.picker-no-search{cursor:default}.picker-menu-list{border-style:none;flex:1 1 auto;min-height:0;overflow-y:auto;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.picker-menu-search+.picker-menu-list.menu{margin-top:-.125rem;padding-top:0}.picker-menu-list.tree{padding:.5rem}.picker-menu-list .tree-item>.selected .item-content{font-weight:400}.picker-menu .search-menu-footer{border-top-width:1px;padding-bottom:.25rem;padding-top:.25rem}.picker-search-input{border-color:transparent;height:1.75rem;outline-width:0!important;padding-left:0;padding-right:2rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color)!important;--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)!important;box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)!important}.picker-search{flex:none;position:relative;width:100%}.picker-search>.magnifier{opacity:.5;position:absolute;right:0;top:.5rem}.picker-search-clear.btn{cursor:pointer;height:1.25rem;position:absolute;right:0;top:.25rem;width:1.25rem}.picker-search.is-inline{min-width:64px;width:4rem}.is-inline>.picker-search-input{height:1.25rem;min-width:64px;padding-left:.25rem;padding-right:.25rem}.picker-search-measure{height:0;left:0;overflow:hidden;position:absolute;top:0;white-space:nowrap}.split{display:flex;flex-direction:row}.split-vert{flex-direction:column}.split-cell{min-height:0;min-width:0}.has-animation>.split-cell{transition-duration:.15s;transition-property:width,height;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter{align-items:stretch;border-radius:var(--radius);cursor:col-resize;display:flex;flex:none;flex-direction:row;justify-content:center;position:relative}.gutter-vert{cursor:row-resize;flex-direction:column}.gutter:before{display:block;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:"";content:var(--tw-content)}.gutter-horz:before{width:1px}.gutter-vert:before{height:1px}.gutter-horz:hover:before{width:75%}.gutter-vert:hover:before{height:75%}.gutter-resize-handler,.gutter-toggle{align-items:center;border-radius:var(--radius-lg);border-width:1px;display:flex;height:1.75rem;justify-content:center;margin-top:-.875rem;position:absolute;top:50%;width:.75rem;--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity));transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter-toggle>span{--tw-scale-x:.75;--tw-scale-y:.75;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter:hover .gutter-toggle{--tw-border-opacity:1;border-color:rgba(var(--color-gray-500-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.gutter .gutter-toggle:hover{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.is-last>.gutter-toggle{--tw-scale-x:-1}.is-first>.gutter-toggle,.is-last>.gutter-toggle{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.is-first>.gutter-toggle{--tw-scale-x:1}.gutter-vert .gutter-toggle{left:50%;margin-left:-.375rem;margin-top:0;top:auto;--tw-rotate:90deg}.gutter-vert .gutter-toggle,.gutter.is-next-collapsed>.gutter-toggle{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.gutter.is-next-collapsed>.gutter-toggle{--tw-scale-x:1}.gutter.is-prev-collapsed>.gutter-toggle{--tw-scale-x:-1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.gutter-horz.is-first.is-prev-collapsed{transform:translateX(calc(-1px - var(--split-gutter-size)/2))}.gutter-horz.is-last.is-next-collapsed{transform:translateX(calc(1px + var(--split-gutter-size)/2))}.gutter-vert.is-first.is-prev-collapsed{transform:translateY(calc(-1px - var(--split-gutter-size)/2))}.gutter-vert.is-last.is-next-collapsed{transform:translateY(calc(1px + var(--split-gutter-size)/2))}.gutter-resize-handler{background-color:transparent;border-width:0}.gutter-resize-handler:before{border-left-width:1px;border-right-width:1px;bottom:0;left:.25rem;position:absolute;right:.25rem;top:0;--tw-content:"";content:var(--tw-content)}.sidebar{flex:none!important;position:relative;--gutter-width:1px;--sidebar-duration:200ms}.has-sidebar-animation .sidebar{transition-duration:.15s;transition-duration:var(--sidebar-duration);transition-property:width,margin;transition-timing-function:cubic-bezier(.4,0,.2,1)}.sidebar-left.is-collapsed{margin-left:calc(var(--gutter-width)*-1)}.sidebar-right.is-collapsed{margin-right:calc(var(--gutter-width)*-1)}.sidebar.is-collapsed>*,.sidebar.is-expanded.is-animating>*{display:none}.sidebar.is-collapsed>.sidebar-gutter{display:flex!important}.sidebar-gutter{bottom:0;left:100%;position:absolute;top:0;width:var(--gutter-width)}.sidebar-right>.sidebar-gutter{left:auto;right:100%}.is-collapsed>.gutter>.gutter-toggle>span{--tw-rotate:-180deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.sidebar-gutter:before{border-radius:var(--radius-full);opacity:0}.sidebar-gutter:hover:before{opacity:1;width:.5rem}.is-expanded .sidebar-gutter.gutter-border:before{opacity:1}.is-sidebar-resizing{cursor:col-resize}:root{--table-head-bg:var(--color-surface);--table-striped-color:var(--color-gray-50);--table-hover-color:rgba(var(--color-primary-500-rgb),.05);--table-border-color:var(--color-border)}.table{border-color:var(--table-border-color);width:100%}.table>thead{background-color:var(--table-head-bg)}.table>*>tr{border-bottom-width:1px}.table>*>tr>*{padding:.5rem 1rem}.table-striped>tbody>tr:nth-child(2n){background:var(--table-striped-color)}.table-hover>tbody>tr:hover>*{background:var(--table-hover-color)}.table.bordered>*>tr>*{border-width:1px}.table.borderless>*>tr,.table.borderless>*>tr>*{border-style:none}.condensed>*>tr>*{padding:.375rem .75rem}.table-fixed{table-layout:fixed}.table-fixed>*>tr>*{overflow:hidden;white-space:nowrap}.toolbar{align-items:center;display:flex;position:relative}.toolbar>.divider{margin:.5rem;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity))}.toolbar-space{flex:1 1 auto;height:1px;width:1px}.toolbar>.dropdown.show{align-items:center;display:flex;position:relative}:root{--tooltip-bg:var(--skin-color,var(--color-inverse));--tooltip-text:var(--skin-text,var(--color-canvas));--tooltip-arrow:6px;--tooltip-delay:0.5s}.hint,[class*=" hint-"],[class^=hint-]{position:relative}.hint:before,[class*=" hint-"]:before,[class^=hint-]:before{border-style:solid;height:0;position:absolute;width:0;--tw-content:"";border-color:var(--tooltip-bg) transparent transparent transparent;border-width:var(--tooltip-arrow) var(--tooltip-arrow) 0 var(--tooltip-arrow);content:var(--tw-content);margin-bottom:calc(0px - var(--tooltip-arrow))}.hint:after,[class*=" hint-"]:after,[class^=hint-]:after{background-color:var(--tooltip-bg);border-color:var(--tooltip-color);border-radius:var(--radius);color:var(--tooltip-text);font-size:.75rem;line-height:1rem;max-width:28rem;overflow:hidden;padding:.25rem .5rem;position:absolute;white-space:nowrap;--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-content:attr(data-hint);content:var(--tw-content);text-shadow:0 1px 0 var(--tooltip-bg)}.hint:after,.hint:before,[class*=" hint-"]:after,[class*=" hint-"]:before,[class^=hint-]:after,[class^=hint-]:before{bottom:100%;left:50%;opacity:0;pointer-events:none;transition-delay:0s;transition-duration:.15s;transition-property:opacity,visibility;transition-timing-function:cubic-bezier(.4,0,.2,1);transition-timing-function:cubic-bezier(.4,0,1,1);visibility:hidden;z-index:1800;--tw-translate-x:-50%;--tw-translate-y:calc(var(--tooltip-arrow)*-1);transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint:hover:after,.hint:hover:before,[class*=" hint-"]:hover:after,[class*=" hint-"]:hover:before,[class^=hint-]:hover:after,[class^=hint-]:hover:before{opacity:1;transition-delay:var(--tooltip-delay);visibility:visible}.hint-bottom:before{border-color:transparent transparent var(--tooltip-bg) transparent;border-width:0 var(--tooltip-arrow) var(--tooltip-arrow) var(--tooltip-arrow);margin-bottom:auto;margin-top:calc(0px - var(--tooltip-arrow))}.hint-bottom:after,.hint-bottom:before{bottom:auto;top:100%;--tw-translate-y:var(--tooltip-arrow);transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-left:before{border-color:transparent transparent transparent var(--tooltip-bg);border-width:var(--tooltip-arrow) 0 var(--tooltip-arrow) var(--tooltip-arrow);margin-bottom:auto;margin-right:calc(0px - var(--tooltip-arrow))}.hint-left:after,.hint-left:before{bottom:50%;left:auto;right:100%;--tw-translate-x:calc(var(--tooltip-arrow)*-1);--tw-translate-y:50%;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-right:before{border-color:transparent var(--tooltip-bg) transparent;border-width:var(--tooltip-arrow) var(--tooltip-arrow) var(--tooltip-arrow) 0;margin-bottom:auto;margin-left:calc(0px - var(--tooltip-arrow))}.hint-right:after,.hint-right:before{bottom:50%;left:100%;--tw-translate-x:var(--tooltip-arrow);--tw-translate-y:50%;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-lg:after,.hint-sm
-.hint-md:after:after,.hint-xl:after{white-space:normal;word-break:break-all}.hint-sm:after{width:4rem}.hint-md:after{width:8rem}.hint-lg:after{width:16rem}.hint-xl:after{width:24rem}.hint-primary{--tooltip-bg:var(--color-primary-500)}.hint-success{--tooltip-bg:var(--color-success-500)}.hint-danger{--tooltip-bg:var(--color-danger-500)}.hint-warning{--tooltip-bg:var(--color-warning-500)}.hint-important{--tooltip-bg:var(--color-important-500)}.hint-special{--tooltip-bg:var(--color-special-500)}.tooltip{background-color:var(--tooltip-bg);border-color:var(--tooltip-color);border-radius:var(--radius);color:var(--tooltip-text);font-size:.75rem;line-height:1rem;max-width:28rem;padding:.25rem .5rem;z-index:1800}.tooltip:not(.white)>.arrow{border-width:0}.tooltip.white>.arrow{border-color:inherit}.tooltip-has-title{--tw-bg-opacity:0.8;padding:.5rem .75rem .75rem;--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.tooltip-has-title>.arrow{opacity:.75}.tooltip-heading{align-items:center;display:flex;font-size:.8125rem;font-weight:700;gap:1rem;justify-content:space-between;line-height:1.25rem;padding:.25rem}.tooltip-heading>.btn-close{margin-right:-.25rem}.tooltip-content{padding:.25rem}.tree-item-inner{flex-direction:row;min-height:24px;padding-left:var(--list-nested-indent)}.tree-item-inner,.tree-toggle{align-items:center;display:flex}.tree-toggle{border-radius:var(--radius);flex:none;height:1rem;justify-content:center;margin-right:-.375rem;width:1rem;--caret-size:5px;--caret-opacity:.3}.tree-item-inner>.item-icon{opacity:.5;width:1rem}.tree-item-inner:hover>.item-icon{opacity:.8}.tree-item-inner.has-hover{border-radius:var(--radius)}.tree-item-inner .item-title:not(:hover),.tree-item-inner>a.item-title:not(:hover){color:inherit}.tree-item-inner>.toolbar{margin-left:1rem;opacity:.6}.tree-item-inner:hover>.toolbar{opacity:1}.tree-item>.active{background:var(--menu-active-bg);color:var(--menu-active-color)}.tree-item>.selected{background:var(--menu-selected-bg)}.tree-item>.selected .item-content{color:var(--menu-selected-color);font-weight:700}.tree.search-menu-on-top>.search-box{left:0;right:0}.tree-lines .tree{position:relative}.tree-lines .tree-item{--tree-line-indent:calc(var(--list-nested-indent) + 8px)}.tree-lines .tree:before{border-left-width:1px;bottom:.5rem;display:block;left:var(--tree-line-indent);position:absolute;top:-.5rem;--tw-content:"";content:var(--tw-content)}.upload .upload-tip{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.upload .draggable-area{background-color:rgba(var(--color-primary-50-rgb),.2);border:1px dashed var(--color-primary-300)}.upload .draggable-area.dragover{background-color:rgba(var(--color-primary-500-rgb),.1);border-style:solid}.upload .upload-tip{color:var(--color-slate-500)}.file-item>.img{height:120px;width:120px}.upload .file-item:hover .file-size{display:flex!important}.form-batch-container{overflow-y:auto}.form-batch-table{min-width:100%;table-layout:fixed;--table-head-bg:var(--color-canvas)}.form-batch-table>*>tr{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.form-batch-table>*>tr>*{padding-left:.375rem;padding-right:.375rem;vertical-align:top}.form-batch-table>*>tr>th{text-align:left;vertical-align:middle}.form-batch-head[data-name=ACTIONS]{width:5rem}.form-batch-head[data-name=ACTIONS][data-action-count="3"]{width:6rem}.form-batch-label{display:inline}.form-batch-control>textarea.form-control{height:2rem}.form-batch-btn+.btn{margin-left:.25rem}.form-batch-table>tbody[data-count="1"] .form-batch-btn[data-type=delete]{display:none}.form-batch-ditto{position:relative}.form-batch-ditto-btn{bottom:0;height:auto;opacity:.5;padding-left:.5rem;padding-right:.5rem;position:absolute!important;right:0;top:0}.form-batch-ditto-btn:after{bottom:.5rem;left:-1px;position:absolute;top:.5rem;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));--tw-content:"";content:var(--tw-content)}[data-ditto=on] .form-batch-ditto-btn{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity));opacity:1}.form-batch-row-actions{padding-bottom:.75rem!important;padding-top:.75rem!important}.form-batch-ditto-wrapper{position:relative}.form-batch-ditto-control .form-control{padding-right:calc(var(--form-batch-ditto-width) + 8px)}.form-batch-ditto-control .input-control>.input-control-suffix{right:var(--form-batch-ditto-width)}.form-batch-ditto-control .input-control>.form-control{padding-right:calc(var(--form-batch-ditto-width) + var(--input-control-suffix))}.form-batch-ditto-control .pick-pri{padding-right:calc(var(--form-batch-ditto-width) + 8px)}.dropmenu-btn{gap:.25rem;padding-left:.5rem;padding-right:.5rem}.dropmenu-btn>.text{max-width:180px;overflow:hidden}.dropmenu-btn>.is-leading{left:-.625rem;opacity:.6;position:absolute}.dropmenu-btn>.is-caret{align-items:center;background-color:rgba(var(--color-canvas-rgb),.2);border-radius:var(--radius);display:flex;height:1rem;justify-content:center;width:1rem}.dropmenu-nav{border-bottom-width:1px;margin-left:.75rem;margin-right:.75rem;margin-top:.25rem}.has-search .dropmenu-nav{margin-top:-.5rem}.dropmenu-nav>.nav-secondary{gap:.5rem}.dropmenu-nav>.nav-secondary>.nav-item>a{border-radius:var(--radius);padding-left:.5rem;padding-right:.5rem}.dropmenu-nav>.nav-secondary>.nav-item>a:after{bottom:-1px;left:1rem;opacity:0;right:1rem}.dropmenu-nav>.nav-secondary>.nav-item>.active:after{left:.5rem;opacity:1;right:.5rem;transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dropmenu-title{font-size:.75rem;font-weight:700;line-height:1rem;margin-bottom:-.5rem;padding:.75rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.dropmenu-list{min-height:0;overflow-x:hidden;overflow-y:auto;padding:.5rem .75rem}.dropmenu.loading>*{opacity:0}.dropmenu-item .tree-item-inner{border-radius:var(--radius);cursor:pointer;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dropmenu-item.is-item.active>.tree-item-inner{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.tree-item-inner.is-link:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.tree-item-inner.is-link:hover .item-content,.tree-item-inner.is-link:hover .item-trailing-icon,.tree-item-inner.is-link:hover .label{color:inherit}.tree-item-inner.is-toggle:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity))}.dropmenu-item+.tree-item{margin-top:.125rem}.dropmenu-item .is-match{font-weight:700;text-decoration-line:underline}.dropmenu-item .item-title,.dropmenu-item .label{overflow:hidden;white-space:nowrap}.dropmenu-item .item-content{padding-left:.375rem;padding-right:.375rem}.dropmenu-item *+.item-content{padding-left:0}.tree-item-inner.is-toggle .item-title{opacity:.6}.tree-item-inner.is-toggle:hover .item-title{opacity:1}.dropmenu-item-check{align-items:center;display:flex;flex:1 1 auto;justify-content:flex-end;padding-right:.5rem}.dropmenu-item .nested-toggle-icon.is-empty{width:.25rem}.dropmenu-item .item-icon{margin-right:-.25rem}:root{--form-control-border:var(--color-border-strong)}.checkbox-primary.disabled,.checkbox-primary.disabled>label,.checkbox-primary>input[type=checkbox]:disabled,.checkbox-primary>input[type=checkbox]:disabled+label,.radio-primary.disabled,.radio-primary.disabled>label,.radio-primary>input[type=radio],.radio-primary>input[type=radio]:disabled+label{filter:none!important}.checkbox-primary.disabled>label,.radio-primary.disabled>label{opacity:1}.form-actions{gap:1rem;justify-content:center}.form-actions .btn{min-width:96px}.form-control-static{min-height:32px;padding-bottom:.375rem;padding-top:.375rem}:root{--zt-panel-form-max-width:1000px}.size-sm{--zt-panel-form-max-width:800px}.size-lg{--zt-panel-form-max-width:1200px}.panel-body>.container,.panel-heading>.container{max-width:var(--panel-container-width);min-width:0;padding-left:var(--panel-container-padding);padding-right:var(--panel-container-padding)}.panel-heading>.container{align-items:center;display:flex;flex-direction:row;flex-wrap:nowrap;gap:1rem;justify-content:space-between;min-height:48px}.panel-form{border-radius:var(--radius-md);margin-bottom:1rem;margin-left:auto;margin-right:auto;max-width:var(--zt-panel-form-max-width);min-width:var(--zt-panel-form-min-width);overflow:visible;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-bottom:1rem;padding-left:1rem;padding-right:1rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.panel-form .form-actions{background-color:rgba(var(--color-canvas-rgb),.8);bottom:0;padding-bottom:1rem;padding-top:1rem;position:sticky;z-index:3;--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.panel-form .form-grid{margin-left:calc(0px - var(--form-grid-gap-y-half));margin-right:calc(0px - var(--form-grid-gap-y-half));padding-bottom:0}.panel-form-toolbar{padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half);width:100%}.panel-form-toolbar>.toolbar{gap:1rem;padding-bottom:.75rem;padding-top:.75rem}.panel-form-divider{margin-bottom:.75rem;margin-top:1rem;padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half);width:100%}.panel-form-divider:before{background-color:rgba(var(--color-border-rgb),.7);display:block;height:1px;--tw-content:"";content:var(--tw-content)}.is-full .btn-full-form,.is-lite .btn-lite-form{z-index:1;--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-300-rgb),var(--tw-ring-opacity))}.btn-toggle-fold:after{content:attr(data-expand-text)}.show-fold-items .btn-toggle-fold:after{content:attr(data-collapse-text)}.is-foldable,.is-full .full\:hidden,.is-full .lite\:visible,.is-full .panel-form-divider,.is-full .panel-form-toolbar,.is-lite .full\:visible,.is-lite .lite\:hidden,.no-foldable-items .btn-toggle-fold{display:none}.is-foldable.is-pinned,.is-full .full\:visible,.is-full .is-foldable,.is-full .lite\:hidden,.is-lite .full\:hidden,.is-lite .lite\:visible,.show-fold-items .is-foldable{display:block}.is-full .full\:w-1\/2,.is-lite .lite\:w-1\/2{width:50%}.is-full .full\:w-1\/3,.is-lite .lite\:w-1\/3{width:33.333333%}.is-full .full\:w-2\/3,.is-lite .lite\:w-2\/3{width:66.666667%}.is-full .full\:w-1\/4,.is-lite .lite\:w-1\/4{width:25%}.is-full .full\:w-2\/4,.is-lite .lite\:w-2\/4{width:50%}.is-full .full\:w-3\/4,.is-lite .lite\:w-3\/4{width:75%}.is-full .full\:w-1\/5,.is-lite .lite\:w-1\/5{width:20%}.is-full .full\:w-2\/5,.is-lite .lite\:w-2\/5{width:40%}.is-full .full\:w-3\/5,.is-lite .lite\:w-3\/5{width:60%}.is-full .full\:w-4\/5,.is-lite .lite\:w-4\/5{width:80%}.is-full .full\:w-1\/6,.is-lite .lite\:w-1\/6{width:16.666667%}.is-full .full\:w-2\/6,.is-lite .lite\:w-2\/6{width:33.333333%}.is-full .full\:w-3\/6,.is-lite .lite\:w-3\/6{width:50%}.is-full .full\:w-4\/6,.is-lite .lite\:w-4\/6{width:66.666667%}.is-full .full\:w-5\/6,.is-lite .lite\:w-5\/6{width:83.333333%}.is-full .full\:w-full,.is-lite .lite\:w-full{width:100%}.page-form{--panel-container-width:960px;--panel-container-padding:20px;--zt-panel-form-max-width:1200px;--zt-panel-form-min-width:1040px;padding-left:0;padding-right:0;--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.page-form .panel-heading{border-bottom-width:1px;--tw-border-opacity:0.7;padding:0}.page-form .panel-title{font-size:1rem;line-height:1.5rem}@media (max-width:1240px){.page-form{--zt-panel-form-max-width:1100px}}@media (max-width:1110px){.page-form{--zt-panel-form-max-width:1040px}}.modal-body>.page-form{margin:-1.5rem -2rem!important;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.modal-body>.page-form>.panel-heading{border-top-left-radius:var(--radius);border-top-right-radius:var(--radius);position:sticky;top:-1.25rem;z-index:2;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-bottom:.375rem;padding-top:.375rem}.modal-body>.panel-form .form-actions{bottom:-1.5rem!important;padding-bottom:1.5rem;padding-top:1.5rem}.dropdown.popover{display:flex;flex-direction:column;position:absolute;z-index:1200}.dropdown.show{display:flex}.dropdown-menu{display:none;--menu-min-width:7rem;--menu-max-width:20rem}.dropdown-menu.show,.menu-wrapper>.dropdown-menu,.show>.dropdown-menu{display:block}.dropdown>.dropdown-menu,.menu-wrapper .dropdown-menu{position:relative}.popup .popup.search-menu{background-color:var(--menu-bg)}.show>.menu-wrapper{display:flex}.dropdown>.menu-wrapper{height:100%}.dropdown>.menu-wrapper .menu-wrapper{position:absolute}.dropdown>.menu-wrapper.is-tree .menu-wrapper{position:relative}.is-contextmenu .is-nested-show>a:not(:hover){--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity))}.is-contextmenu .menu-item.is-nested>.item-inner>.nested-toggle-icon{position:absolute;right:.25rem;top:.375rem}.is-contextmenu .menu-nested .menu-item>.item-inner{padding-left:.5rem;padding-right:1.25rem}.is-contextmenu .menu-nested .menu-item>.item-inner>.item-content{overflow:hidden}.dropdown>.arrow{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.global-search-panel li:not(.order-first):hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.global-search-panel li a{width:100%}.global-search-panel li{cursor:pointer}.history-panel>.panel-heading+.panel-body{margin-top:-.75rem}.history-panel-action{position:relative}.history-panel-action:before{border-left-width:1px;bottom:-.375rem;left:.5rem;position:absolute;top:22px;--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-content:"";content:var(--tw-content)}.col-reverse>.history-panel-action:first-child:before,.col>.history-panel-action:last-child:before{display:none}.history-panel-action>.item-inner{padding-left:1.5rem}.history-panel-action>.item-inner>.avatar{left:0;position:absolute;top:.375rem}.img-cutter{background:var(--color-gray-100);border:1px solid #ddd;margin-bottom:20px;padding:10px}.img-cutter .canvas{margin:0 auto;max-width:100%;min-width:50px;position:relative}.img-cutter .cover{bottom:0;left:0;position:absolute;right:0;top:0;z-index:1}.img-cutter .controller{background:none;border:1px dashed hsla(0,0%,100%,.7);cursor:move;position:absolute;z-index:5}.img-cutter .control{background:#000;background:rgba(0,0,0,.6);border:1px solid hsla(0,0%,100%,.6);height:6px;position:absolute;width:6px}.img-cutter .control[data-type=left]{cursor:w-resize;left:-4px;margin-top:-3px;top:50%}.img-cutter .control[data-type=top]{cursor:n-resize;left:50%;margin-left:-3px;top:-4px}.img-cutter .control[data-type=right]{cursor:e-resize;margin-top:-3px;right:-4px;top:50%}.img-cutter .control[data-type=bottom]{bottom:-4px;cursor:s-resize;left:50%;margin-left:-3px}.img-cutter .control[data-type=top-left]{cursor:nw-resize;left:-4px;top:-4px}.img-cutter .control[data-type=top-right]{cursor:ne-resize;right:-4px;top:-4px}.img-cutter .control[data-type=bottom-left]{bottom:-4px;cursor:sw-resize;left:-4px}.img-cutter .control[data-type=bottom-right]{bottom:-4px;cursor:se-resize;right:-4px}.img-cutter .cliper{bottom:0;left:0;position:absolute;right:0;top:0;z-index:2}.messager-lite{border-radius:var(--radius-lg);min-width:160px;--tw-bg-opacity:1!important;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))!important;padding:1rem 1.5rem;--tw-text-opacity:1!important;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))!important;--skin-ring:transparent!important;--skin-text:inherit!important;--skin-color:var(--color-gray-500)}.messager-lite .alert-icon{color:var(--skin-color);font-size:1.5rem;line-height:2rem}.messager-lite .alert-text{font-size:.875rem;font-weight:700;line-height:1.3rem}.messager-lite .toolbar{gap:.5rem;margin-left:2rem}.messager-lite .alert-content+.alert-close{margin-left:1.5rem}.messager-lite .toolbar .btn.ghost{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.modal-reconfirm .modal-body{font-size:14px;font-weight:700;padding:24px 32px}.modal-reconfirm .modal-footer{justify-content:center;padding:24px}.picker-deselect-btn{opacity:.6;transition-duration:.15s;transition-property:opacity,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.picker-multi-selection{cursor:pointer;padding-right:.5rem;position:relative}.picker-multi-selection .picker-deselect-btn{bottom:0;left:0;position:absolute;right:0;top:0;--tw-scale-x:0;--tw-scale-y:0;background-color:rgba(var(--color-surface-rgb),.8);opacity:0}.picker-deselect-btn:hover,.picker-multi-selection .picker-deselect-btn,.picker-multi-selection:hover .picker-deselect-btn{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.picker-deselect-btn:hover,.picker-multi-selection:hover .picker-deselect-btn{--tw-scale-x:1;--tw-scale-y:1;opacity:1;--state-color:rgba(var(--color-surface-rgb),.9)}.pick-pri{flex-direction:row;justify-content:flex-start;position:relative}.pick-pri,.pick-pri>.text{align-items:center;display:flex}.pick-pri>.text{flex:1 1 auto;min-width:0;overflow:hidden;white-space:nowrap}.pick-pri .placeholder{--tw-text-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-text-opacity))}.pick-pri-list>.btn{justify-content:flex-start}.disabled.pick-pri,.disabled.pick-pri>*{filter:none}.search-form{--gutter-width:12px;padding-bottom:.5rem}.search-form-container{border-radius:var(--radius);min-height:116px;position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.is-simple .search-form-container{min-height:56px}.search-form-field td{padding:.375rem}.search-form-field td.is-andOr,.search-form-field td.is-operator{width:5rem}.search-form-field td.is-condition{width:7rem}.search-form-field td.is-operator{width:5rem}[lang=en] .search-form-field td.is-operator{width:6rem}.search-form .sidebar-right.is-collapsed{margin-right:-.375rem}.is-simple .search-form-wrapper{display:flex}.is-simple .search-form-wrapper>.row{flex:1 1 auto}.is-simple .search-form-wrapper>.toolbar{flex:none;margin-top:0}.zinbar [data-hint]{position:relative}.zinbar [data-hint]:after{background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity));border-top-left-radius:var(--radius-lg);border-top-right-radius:var(--radius-lg);bottom:100%;display:block;pointer-events:none;position:absolute;right:0;white-space:nowrap;z-index:50;--tw-bg-opacity:0.9;font-size:.75rem;line-height:1rem;padding:.125rem .25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:attr(data-hint);content:var(--tw-content)}.zinbar [data-hint]:hover:after{opacity:1}.zin-perf-btn-list .text-danger{color:var(--color-danger-400)}.zinbar .state{transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.zinbar .state:active{--tw-scale-x:1.05;--tw-scale-y:1.05}.zinbar .state:active,.zinbar.collapse{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.zinbar.collapse{--tw-translate-x:100%}.zinbar.collapse>div{pointer-events:none}.zinbar{--tw-translate-x:0px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));transition-duration:.7s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}body[z-perf=danger]:before,body[z-perf=warning]:before{bottom:0;left:0;pointer-events:none;position:fixed;right:0;top:0;z-index:9990;--tw-border-opacity:1;border-color:rgba(var(--color-warning-600-rgb),var(--tw-border-opacity));font-size:.75rem;line-height:1rem;--tw-content:"";border-style:inset;border-width:12px 8px 8px;content:var(--tw-content)}body[z-perf=danger]:before{--tw-border-opacity:1;border-color:rgba(var(--color-danger-600-rgb),var(--tw-border-opacity))}body[z-perf=danger]:after,body[z-perf=warning]:after{font-size:.75rem;font-weight:700;left:0;line-height:1rem;line-height:1;pointer-events:none;position:fixed;right:0;text-align:center;top:0;z-index:9991;--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity));--tw-content:attr(z-perf-message);content:var(--tw-content)}.card{border-radius:var(--radius);min-height:28px;position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;transition-duration:.15s;transition-property:box-shadow,border,color,background-color;transition-timing-function:cubic-bezier(.4,0,.2,1)}.card:hover{--tw-shadow:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--tw-shadow-colored:0 2px 6px -1px var(--tw-shadow-color),0 1px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.card-content,.card-footer,.card-header,.card-heading{padding:.25rem .5rem}.card-heading{align-items:center;display:flex;gap:.5rem}.card-icon{opacity:.5}.card-header{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.card-content{display:flex;flex-direction:column;gap:.25rem}.card-actions{position:absolute;right:.125rem;top:.125rem}.card-actions+.card-heading{padding-right:1.75rem}.card-subtitle{font-size:.75rem;line-height:1rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.card.selected{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-400-rgb),var(--tw-ring-opacity))}.card-list{--list-gap:.625rem;--list-count-per-row:1}.card-list,.card-list-item{padding:calc(var(--list-gap)/2)}.card-list-item{width:calc(100%/var(--list-count-per-row))}.card-grid{display:flex;flex-wrap:wrap}.card-grid .card{height:100%}.contextmenu{display:none}.contextmenu.show{display:block}.contextmenu .popup .popup,.contextmenu.popup{position:absolute}.more,.more-vert{margin:.5rem;position:relative}.more,.more-vert,.more-vert:after,.more-vert:before,.more:after,.more:before{background-color:currentColor;border-radius:var(--radius-full);height:.125rem;width:.125rem}.more-vert:after,.more-vert:before,.more:after,.more:before{display:block;left:-5px;position:absolute;top:0;--tw-content:"";content:var(--tw-content)}.more-vert:after,.more:after{left:5px}.more-vert{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dashboard-blocks{position:relative}.dashboard-block-cell{position:absolute;transition-duration:.15s;transition-property:left,top;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-block{border-radius:var(--radius);bottom:.5rem;left:.5rem;position:absolute;right:.5rem;top:.5rem;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-block.is-dragging{opacity:0;z-index:1600}.dashboard-block-header{align-items:center;border-top-left-radius:var(--radius);border-top-right-radius:var(--radius);display:flex;flex-direction:row;justify-content:space-between;left:0;padding:.75rem;pointer-events:none;position:absolute;right:0;top:0;z-index:10}.dashboard-block-header>*{pointer-events:auto}.dashboard-block-title{font-size:.875rem;font-weight:700;line-height:1.3rem}.dashboard-block-body{bottom:0;left:0;position:absolute;right:0;top:0}.dashboard-block-body>.panel{display:flex;flex-direction:column;height:100%;width:100%;--tw-shadow:0px 6px 16px rgba(202,215,235,.25)}.dashboard-block-body .panel-heading{cursor:move;flex:none}.dashboard-block-body .panel-body{flex:1 1 auto;overflow-y:auto}.has-more-menu>.dashboard-block-body .panel-heading{padding-right:3rem}.dashboard-block-body .panel-title{font-size:.875rem;height:2rem;line-height:1.3rem}.dashboard-block-actions .btn{opacity:.6}.dashboard-block-actions .btn:hover{opacity:1}.dashboard-drop-shadow{position:absolute;transition-duration:.15s;transition-property:left,top;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-drop-shadow:before{background-color:rgba(var(--color-inverse-rgb),.05);border-radius:var(--radius);bottom:.5rem;left:.5rem;position:absolute;right:.5rem;top:.5rem;--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-content:"";content:var(--tw-content)}.scrollbar,:root{--scrollbar-size:10px;--scrollbar-opacity:.6;--scrollbar-bg:rgba(var(--color-inverse-rgb),.15);--scrollbar-inset:inset 0 0 0 1px rgba(var(--color-inverse-rgb),.05);--scrollbar-bar-bg:rgba(var(--color-inverse-rgb),.3);--scrollbar-hover-bg:rgba(var(--color-inverse-rgb),.4);--scrollbar-drag-bg:rgba(var(--color-inverse-rgb),.5);--scrollbar-radius:var(--radius-sm);--scrollbar-duration:.7s}.scrollbar{background:var(--scrollbar-bg);box-shadow:var(--scrollbar-shadow);opacity:var(--scrollbar-opacity);position:absolute;transition-duration:.15s;transition-duration:var(--scrollbar-duration);transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.scrollbar-hover .scrollbar{opacity:0}.scrollbar-hover:hover .scrollbar{opacity:var(--scrollbar-opacity)}.scrollbar.is-dragging,.scrollbar:hover{opacity:1!important}.scrollbar-bar{background:var(--scrollbar-bar-bg);border-radius:var(--scrollbar-radius);position:absolute}.scrollbar-bar:hover{background:var(--scrollbar-hover-bg)}.is-dragging>.scrollbar-bar{background:var(--scrollbar-drag-bg)}.is-horz>.scrollbar-bar{height:100%;z-index:20}.is-vert>.scrollbar-bar{width:100%;z-index:20}:root{--dtable-checked-bg:var(--color-warning-50);--dtable-checked-bg-hover:var(--color-warning-100);--dtable-checked-border:var(--color-border-strong)}.dtable-cell.is-checked,.dtable-striped .dtable-cell.is-odd-row.is-checked{background-color:var(--dtable-checked-bg)}.checkbox-primary.dtable-checkbox{margin-right:-.375rem}.dtable-checkbox{order:-5}.dtable-hover-col .dtable-cell.is-hover-col.is-checked,.dtable-hover-row .dtable-cell.is-hover-row.is-checked{background-color:var(--dtable-checked-bg-hover)}.dtable-cell.is-checked{--dtable-border-color:var(--dtable-checked-border)}.dtable-check-info{flex-shrink:1;margin-right:.5rem;overflow:hidden;white-space:nowrap}:root{--toggle-icon-size:calc(var(--font-size-root)*3/4 + 1px)}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-color:currentColor;border-width:1px;display:block;opacity:.5;position:relative}.toggle-icon-collapse:hover,.toggle-icon-expand:hover,.toggle-icon:hover{opacity:.9}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-radius:inherit;height:var(--toggle-icon-size);width:var(--toggle-icon-size)}.is-collapsed .toggle-icon:after,.is-collapsed .toggle-icon:before,.is-expanded .toggle-icon:before,.toggle-icon-collapse:after,.toggle-icon-collapse:before,.toggle-icon-expand:before{background-color:currentColor;content:" ";display:block;height:1px;left:2px;position:absolute;right:2px;top:calc((var(--toggle-icon-size) - 3px)/2)}.is-collapsed .toggle-icon:after,.toggle-icon-collapse:after{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:root{--dtable-nt-size:calc(var(--font-size-root)*3/4 + 1px)}.dtable-nested-indent{flex:none;margin-right:-.25rem;order:-100}.dtable-nested-toggle{align-items:center;border-radius:var(--radius-sm);display:flex;flex:none;height:1.25rem;justify-content:center;margin-left:-.25rem;order:-6;width:1.25rem}.dtable-nested-toggle.is-no-child{margin-right:-.25rem;opacity:0;pointer-events:none}.dtable-child-label{order:-5}.dtable-header-group{align-items:center;background:var(--dtable-header-bg);cursor:default;display:flex;justify-content:center;left:0;position:absolute;top:1px;z-index:30}.dtable-bordered .dtable-header-group{border-bottom:1px solid var(--dtable-border-color);border-left:1px solid var(--dtable-border-color)}.dtable-header-as-group{contain:style;content-visibility:visible;overflow:visible!important}.dtable-sorting{cursor:move}.dtable-cell.is-sorting-from{background-color:var(--dtable-bg);z-index:20}.dtable-cell.is-sorting-from:before{border-top-width:1px}.dtable-sorting .dtable-cell.is-sorting-after{--tw-translate-y:-100%}.dtable-sorting .dtable-cell.is-sorting-after,.dtable-sorting .dtable-cell.is-sorting-before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dtable-sorting .dtable-cell.is-sorting-before{--tw-translate-y:100%}.dtable-cell.is-sorting-before:before,.dtable-cell.is-sorting-from:before{border-bottom-width:1px;border-top-width:1px}.dtable{--dtable-bg:var(--color-canvas);--dtable-striped-bg:var(--color-gray-50);--dtable-hover-bg:rgba(var(--color-primary-500-rgb),.05);--dtable-header-bg:var(--color-surface);--dtable-footer-bg:var(--color-surface);--dtable-border-color:var(--color-border);--dtable-sorter-size:0.3125rem}.dtable{position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.dtable.no-animation *{transition-property:none!important}.dtable-block{overflow:hidden;position:absolute;width:100%}.dtable-header{background-color:var(--dtable-header-bg);border-top-left-radius:inherit;border-top-right-radius:inherit}.dtable-body{overflow:hidden}.dtable-cells{background-color:var(--dtable-bg);height:100%;position:absolute;z-index:0}.dtable-cells-container{height:100%;position:absolute;width:100%}.dtable-header .dtable-cells{background-color:var(--dtable-header-bg)}.dtable-cells.dtable-fixed-left,.dtable-cells.dtable-fixed-right{z-index:10}.dtable-cell{position:absolute;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-cell:after,.dtable-cell:before{bottom:0;content:"";left:0;opacity:0;pointer-events:none;position:absolute;right:0;top:-1px;z-index:2}.dtable-cell:before{border-bottom-width:1px;border-color:var(--dtable-border-color);opacity:1}.dtable-header-cell{align-items:center;display:flex;font-weight:700}.dtable-header-cell:after,.dtable-header-cell:before{top:0}.dtable-cell-content{align-items:center;display:flex;gap:.25rem;height:100%;overflow:hidden;padding-left:.75rem;padding-right:.75rem;position:relative;white-space:nowrap;width:100%;z-index:5}.dtable-body .dtable-cell.is-last-row:before{border-bottom-width:0}.dtable-footer{align-items:center;background-color:var(--dtable-footer-bg);border-bottom-left-radius:inherit;border-bottom-right-radius:inherit;border-color:var(--dtable-border-color);border-top-width:1px;display:flex;padding-left:.75rem;padding-right:.75rem;position:absolute;width:100%;z-index:10}.dtable-empty-tip{align-items:center;display:flex;height:100%;justify-content:center}.dtable .scrollbar{z-index:20}.dtable-header{transition-duration:1s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-scrolled-down .dtable-header{border-bottom-color:rgba(var(--color-inverse-rgb),.15);border-bottom-width:1px}.dtable-has-scroll-y:not(.dtable-scrolled-bottom) .dtable-footer{border-top-color:rgba(var(--color-inverse-rgb),.15);border-top-width:1px}.dtable-scroll-shadow{background-image:linear-gradient(90deg,rgba(0,0,0,.03),transparent),linear-gradient(90deg,rgba(0,0,0,.03),transparent 50%);opacity:0;pointer-events:none;position:absolute;top:0;transition-duration:1s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:8px;z-index:20}.dtable:hover .dtable-scroll-shadow{opacity:1}.dtable-scroll-shadow.is-right{margin-left:-7px;--tw-rotate:180deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dtable-scroll-shadow.is-left,.dtable-scrolled-end .dtable-scroll-shadow.is-right{visibility:hidden}.dtable-scroll-shadow.is-right,.dtable-scrolled-right .dtable-scroll-shadow.is-left{visibility:visible}.scrollbar-hover:hover .scrollbar{opacity:0}.scrollbar-hover .dtable-body:hover~.scrollbar{opacity:var(--scrollbar-opacity)}.dtable-sort{display:inline-flex;height:calc(var(--dtable-sorter-size)*12/5);margin-left:.25rem;opacity:.8;position:relative}.dtable-cell:hover .dtable-sort{opacity:1}.dtable-sort:after,.dtable-sort:before{border-color:transparent;border-style:solid;height:0;left:0;opacity:.4;position:absolute;width:0;--tw-content:"";border-width:var(--dtable-sorter-size);content:var(--tw-content)}.dtable-sort:before{border-bottom-color:currentColor;border-top-width:0;top:0}.dtable-sort:after{border-bottom-width:0;border-top-color:currentColor;bottom:0}.dtable-sort.dtable-sort-asc:before,.dtable-sort.dtable-sort-desc:after{opacity:.9}.dtable-sort-link{align-items:center;cursor:pointer;display:inline-flex}.dtable-cells.dtable-fixed-left:before,.dtable-cells.dtable-fixed-right:before{border-color:var(--dtable-border-color);content:"";height:100%;pointer-events:none;position:absolute;width:100%;z-index:5}.dtable-cells.dtable-fixed-left:before{border-right-width:1px;right:-1px}.dtable-cells.dtable-fixed-right:before{border-left-width:1px;left:0}.dtable-bordered:before{border-color:var(--dtable-border-color);border-radius:inherit;border-width:1px;bottom:0;content:"";display:block;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:15}.dtable-bordered .dtable-cell:before{border-width:1px;right:-1px}.dtable-cell.has-border-left:before{border-left-width:1px}.dtable-cell.has-border-right:before{border-right-width:1px;right:-1px}.dtable-striped .dtable-cell.is-odd-row{background-color:var(--dtable-striped-bg)}.dtable-hover-cell .dtable-cell:hover:after,.dtable-hover-col .dtable-cell.is-hover-col:before,.dtable-hover-row .dtable-body .dtable-cell.is-hover-row:before{background-color:var(--dtable-hover-bg)}.kanban{--kanban-lane-name-width:20px;--kanban-col-width:280px;--kanban-cols-gap:8px;--kanban-lanes-gap:8px;--kanban-header-height:32px;--kanban-lane-height:auto;--kanban-lane-color:var(--color-primary-500);--kanban-link-color:var(--color-secondary-600)}.kanban{align-items:flex-start;display:flex;flex-direction:column;min-width:-moz-fit-content;min-width:fit-content;position:relative}.kanban-header{display:flex;flex-direction:row;height:var(--kanban-header-height)}.kanban.has-sub-cols .kanban-header{height:calc(var(--kanban-header-height)*2)}.kanban-header-lane-name{background-color:rgba(var(--color-fore-rgb),.05);flex:none;width:var(--kanban-lane-name-width)}.kanban-header-cols,.kanban-header-sub-cols{display:flex;flex:1 1 0%;flex-direction:row;gap:var(--kanban-cols-gap)}.kanban-header-sub-cols{border-top-width:2px;--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity))}.kanban-header-col{align-items:center;border-bottom-width:1px;display:flex;flex:1 1 0%;flex-direction:column;height:100%;width:var(--kanban-col-width)}.kanban-header-col.has-subs{width:auto}.kanban-header-col-wrapper{align-items:center;display:flex;flex:1 1 0%;flex-direction:row;position:relative;width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:3.5rem;padding-right:3.5rem}.kanban-header-col-wrapper.is-align-left{justify-content:flex-start;padding-left:.5rem}.kanban-header-col-wrapper.is-align-left>.kanban-header-title{justify-content:flex-start}.kanban-header-title{align-items:center;display:flex;flex:1 1 auto;flex-direction:row;justify-content:center;overflow:hidden}.kanban-header-title>.as-title{color:var(--kanban-col-color);font-weight:700;overflow:hidden;white-space:nowrap}.kanban-header-col-actions{bottom:.25rem;position:absolute;right:.25rem;top:.25rem}.kanban-header-col-actions>.btn{opacity:.6}.kanban-header-col-actions>.btn:hover{opacity:1}.kanban-body{display:flex;flex-direction:column;gap:var(--kanban-lanes-gap)}.kanban-lane{display:flex;flex-direction:row;height:var(--kanban-lane-height);min-height:96px}.kanban-lane-name{align-items:center;background-color:var(--kanban-lane-color);display:flex;justify-content:center;width:var(--kanban-lane-name-width);--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity));writing-mode:vertical-rl}.kanban-lane-actions,.kanban-lane-name{flex:none;position:relative}.kanban-lane.is-first .kanban-lane-actions{margin-top:calc(4px - var(--kanban-header-height))}.has-sub-cols .kanban-lane.is-first .kanban-lane-actions{margin-top:calc(4px - var(--kanban-header-height)*2)}.kanban-lane-actions>.btn.square{width:var(--kanban-lane-name-width)}.kanban-lane-title{align-items:center;display:flex;flex:1 1 auto;justify-content:center;overflow:hidden;white-space:nowrap}.kanban-lane-cols{display:flex;flex-direction:row;gap:var(--kanban-cols-gap)}.kanban-lane-col{background-color:rgba(var(--color-inverse-rgb),.05);display:flex;flex-direction:column;height:100%;width:var(--kanban-col-width)}.kanban-header-col,.kanban-lane-col{margin-left:calc(var(--kanban-col-gap-left) - var(--kanban-cols-gap));margin-right:calc(var(--kanban-col-gap-right) - var(--kanban-cols-gap))}.kanban-col-content{position:relative;z-index:5}.kanban-lane.is-first>.kanban-lane-name:before{background-color:var(--kanban-lane-color);bottom:100%;display:block;height:var(--kanban-header-height);left:0;position:absolute;right:0;--tw-content:"";content:var(--tw-content)}.kanban.has-sub-cols .kanban-lane.is-first>.kanban-lane-name:before{height:calc(var(--kanban-header-height)*2)}.kanban-lane{margin-bottom:calc(var(--kanban-col-gap-bottom) - var(--kanban-lanes-gap));margin-top:calc(var(--kanban-col-gap-top) - var(--kanban-lanes-gap))}.kanban-items{flex:1 1 auto;overflow:auto;scrollbar-gutter:both-edges stable}.kanban-lane.is-auto-height .kanban-items{scrollbar-gutter:auto}.kanban-item{cursor:default}.kanban-item .card-actions{z-index:5}.kanban-heading{width:100%}.kanban-heading .listitem{height:2.25rem}.kanban-heading .item-title{font-weight:700}.kanban.has-dragging{cursor:move}.kanban-item.is-dragging{cursor:move;opacity:.1}.kanban-sticky .kanban-header{position:sticky;top:0;z-index:10;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.kanban-sticky .kanban-header.is-pinned{border-bottom-color:rgba(var(--color-inverse-rgb),.15);border-bottom-width:1px;z-index:20;--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.kanban-sticky .kanban-lane-name{left:0;position:sticky;z-index:21}.kanban-region{border-radius:var(--radius);min-width:-moz-fit-content;min-width:fit-content;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding:.75rem;--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.kanban-region>.kanban+.kanban{margin-top:.75rem}.kanban-region.has-heading{padding-top:0}.kanban-heading>.listitem{left:.75rem;position:sticky;width:calc(var(--kanban-list-width) - 24px)}.kanban-list{display:flex;flex-direction:column;gap:.75rem;height:100vh;overflow:auto;position:relative;scrollbar-gutter:stable}.kanban-list.is-moving{cursor:grabbing}.kanban-items.is-dropping{position:relative}.kanban-item.is-dropping{position:relative;transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.kanban-item.is-dropping:after,.kanban-items.is-dropping>.card-list:after{background-color:rgba(var(--color-warning-500-rgb),.5);border-radius:var(--radius-full);display:block;height:.25rem;--tw-content:"";content:var(--tw-content)}.kanban-item.is-dropping:after{left:.25rem;position:absolute;right:.25rem;top:-.25rem}.kanban-item.is-dropping[z-drop-side=before]{--tw-translate-y:0.25rem}.kanban-item.is-dropping[z-drop-side=after],.kanban-item.is-dropping[z-drop-side=before]{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-item.is-dropping[z-drop-side=after]{--tw-translate-y:-0.25rem}.kanban-item.is-dropping[z-drop-side=after]:after{bottom:-.25rem;top:auto}.kanban-links{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:5}.kanban-list>.kanban-links{overflow:visible;z-index:11}.kanban-link{align-items:center;color:var(--kanban-link-color);display:flex;justify-content:center;position:absolute}.kanban-link>svg{position:absolute}.kanban-link-text{border-radius:var(--radius);height:1em;line-height:1;padding-left:.125rem;padding-right:.125rem;pointer-events:auto;position:relative;text-align:center;white-space:nowrap}.kanban-link-start-point{height:.5rem;width:.5rem;--tw-translate-x:-0.25rem;--tw-translate-y:-0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-start-point,.kanban-link-start-point:before{background-color:currentColor;border-radius:var(--radius-full);position:absolute}.kanban-link-start-point:before{bottom:-.25rem;display:block;left:-.25rem;opacity:.2;right:-.25rem;top:-.25rem;--tw-content:"";content:var(--tw-content)}.kanban-link path{pointer-events:auto}.kanban-link path+path{opacity:.6}.kanban-link.is-hover path+path{opacity:1;stroke-width:calc(var(--kanban-link-weight)*1.5)}.kanban-link-delete-btn{pointer-events:auto;--tw-scale-x:.75;--tw-scale-y:.75;opacity:0;transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.is-hover .kanban-link-delete-btn,.kanban-link-delete-btn{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.is-hover .kanban-link-delete-btn{--tw-scale-x:1;--tw-scale-y:1;opacity:1}.is-adding-link{cursor:crosshair;-webkit-user-select:none;-moz-user-select:none;user-select:none}.kanban-link-editor{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:20}.kanban-link-editor-from,.kanban-link-editor-to{border-radius:var(--radius);--tw-shadow-color:rgb(var(--color-primary-500-rgb));--tw-shadow:var(--tw-shadow-colored);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-500-rgb),var(--tw-ring-opacity))}.kanban-link-editor-from,.kanban-link-editor-point,.kanban-link-editor-to{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);position:absolute}.kanban-link-editor-point{height:.5rem;pointer-events:auto;width:.5rem;--tw-translate-x:-0.25rem;--tw-translate-y:-0.25rem;border-radius:var(--radius-full);cursor:move;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));opacity:.5;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(4px + var(--tw-ring-offset-width)) var(--tw-ring-color);--tw-ring-color:rgba(var(--color-primary-500-rgb),0.1);transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.kanban-link-editor-point.is-left{left:0;top:50%}.kanban-link-editor-point.is-right{right:0;top:50%;--tw-translate-x:0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-editor-point.is-top{left:50%;top:0}.kanban-link-editor-point.is-bottom{bottom:0;left:50%;--tw-translate-y:0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-editor-point:hover{opacity:1;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(8px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-primary-500-rgb),0.5)}.tab-pane{display:none}.tab-pane.active{display:block}.has-sorting-col{cursor:move;--dtable-sorting-col-color:var(--color-primary-300);--dtable-hover-bg:transparent}.has-sorting-col .dtable-col-splitter{display:none}.dtable-cell.is-sorting-col-move{transition-duration:.15s;transition-property:left;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-cell.is-sorting-from-col{transition-duration:.1s}.dtable-cell.is-sorting-from-col:after{background-color:var(--dtable-sorting-col-color)!important;opacity:.1!important}.dtable-cell.is-sorting-from-col:before{border-left:1px solid var(--dtable-sorting-col-color);border-right:1px solid var(--dtable-sorting-col-color)}.dtable-header-cell.is-sortable-col{cursor:move}.has-sorting-col .scrollbar.is-horz{opacity:var(--scrollbar-opacity)!important}.has-sorting-col .dtable-scroll-shadow{visibility:visible}:root{--dtable-col-splitter-width:7px;--dtable-col-splitter-color:var(--color-primary-500)}.dtable-cell.has-col-resizing:after,.dtable-cell.has-col-splitter:hover:after{background:var(--dtable-col-splitter-color);opacity:.05}.dtable-col-splitter{background:var(--dtable-col-splitter-color);border-radius:var(--radius-full);bottom:0;cursor:ew-resize;opacity:0;position:absolute;right:calc(var(--dtable-col-splitter-width)/-2);top:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:var(--dtable-col-splitter-width);z-index:20}.dtable-cell.has-col-splitter:hover .dtable-col-splitter{opacity:.3}.dtable-cell.has-col-resizing .dtable-col-splitter,.dtable-cell.has-col-splitter .dtable-col-splitter:hover{opacity:.5}.dtable.has-col-resizing .dtable-cell.has-col-splitter:not(.has-col-resizing) .dtable-col-splitter,.dtable.has-col-resizing .dtable-cell.has-col-splitter:not(.has-col-resizing):after{opacity:0}.dtable-col-splitter:after,.dtable-col-splitter:before{content:" ";display:block;height:.5rem;left:50%;margin-top:-.25rem;position:absolute;top:50%;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity))}.dtable-col-splitter:before{margin-left:-1px}.dtable-col-splitter:after{margin-left:1px}.dtable.has-col-resizing{--dtable-hover-bg:transparent}.dtable.has-col-resizing,.has-col-resizing .dtable-header-cell{cursor:ew-resize!important}.dtable-cell.is-col-resizing:before{border-right:1px solid var(--dtable-col-splitter-color)}.dtable-cell.is-col-resizing:after{background:var(--dtable-col-splitter-color);opacity:.05}.has-col-resizing .scrollbar.is-horz{opacity:var(--scrollbar-opacity)!important}.dtable-cell.has-contextmenu-show:after{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));opacity:.1}.dtable{--dtable-header-bg:var(--color-surface-light);--dtable-footer-bg:var(--color-surface-light);--dtable-border-color:var(--color-border-light);--dtable-checked-border:var(--color-border);--dtable-checked-bg:var(--color-primary-50);--dtable-checked-bg-hover:var(--color-primary-100);--dtable-hover-bg:rgba(var(--color-gray-500-rgb),.05);--dtable-link-color:var(--color-link);--dtable-link-hover-color:var(--color-link-hover);--dtable-link-visited-color:var(--color-link-visited)}.dtable-cell-content[style*="--color-link"]{--dtable-link-hover-color:var(--color-link);--dtable-link-visited-color:var(--color-link)}.dtable-body .dtable-cell a{--dtable-link-color:var(--color-link)}.dtable-body .dtable-cell a:not(.btn){color:var(--dtable-link-color)}.dtable-body .dtable-cell a:not(.btn):visited{color:var(--dtable-link-visited-color)}.dtable-body .dtable-cell a:not(.btn):hover{color:var(--dtable-link-hover-color)}.dtable .btn-avatar{border-radius:var(--radius-full);gap:.25rem;height:1.25rem;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity));padding-left:0;padding-right:.5rem;--tw-ring-color:transparent}.dtable .btn-avatar:hover{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.dtable-nested-toggle{width:1rem}.dtable .toggle-icon{--toggle-icon-size:11px;border-radius:var(--radius);--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.dtable .toggle-icon:after,.dtable .toggle-icon:before{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-700-rgb),var(--tw-bg-opacity))}.dtable-footer>.toolbar{margin-right:.5rem}.dtable-header .dtable-cell[data-sort]>.dtable-cell-content>a:not(:hover){color:inherit}.dtable-assign-btn{align-items:center;border-radius:var(--radius-full);display:flex;flex-direction:row;height:1.25rem;padding-left:.375rem;padding-right:.375rem;--dtable-link-color:var(--color-fore)}.dtable-assign-btn:not(:hover){color:inherit}.dtable-assign-btn.is-me{--dtable-link-color:var(--color-warning-500)!important}.dtable-assign-btn:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.dtable-assign-btn>span{border-radius:var(--radius-full);line-height:20px;padding-left:.375rem;padding-right:.375rem}.dtable-assign-btn.is-unassigned>span{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.dtable-assign-btn.is-unassigned:hover>span{background-color:inherit;color:inherit;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.dtable-assign-btn>.icon{opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-assign-btn:not(.disabled):hover>.icon{opacity:1}.dtable-header .dtable-cell[data-type=assign]{padding-left:1.5rem}.dtable-cell-icon{order:-5}.dtable-custom-cell[data-type=control]{align-items:center;display:flex;justify-content:center;padding-left:.125rem;padding-right:.125rem;z-index:1}.dtable-empty-tip{min-height:212px}.dtable-cell[data-type=actions] .btn>.icon{font-size:1rem;line-height:1.5rem}.menu.menu-dtable-actions.has-icons{align-items:center;display:flex;gap:.25rem;min-width:auto;--menu-icon-opacity:1}.menu.menu-dtable-actions.has-icons>.menu-item>a{padding-left:.25rem;padding-right:.25rem}.menu.menu-dtable-actions.has-icons>.menu-item>a>.icon-EMPTY,.menu.menu-dtable-actions.has-icons>.menu-item>a>.item-content{display:none}.menu.menu-dtable-actions.has-icons>.menu-item>a>.icon-EMPTY+.item-content,.menu.menu-dtable-actions.has-icons>.menu-item>a>.item-content:first-child{display:block}:root{--state-color:rgba(0,0,0,.03);--zt-page-bg:#f8f9fa;--zt-header-height:3rem;--zt-header-bg:var(--color-canvas);--zt-header-color:var(--color-fore);--zt-sidebar-width:160px;--zt-navbar-active-color:var(--color-primary-500)}body{background-color:var(--zt-page-bg)}.page-app{overflow:overlay}.container{min-width:1200px}#header{height:var(--zt-header-height);--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);background:var(--zt-header-bg);border-bottom:1px solid var(--zt-header-border,rgba(var(--color-inverse-rgb),.05));box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);color:var(--zt-header-color)}#header>.container{height:100%;position:relative}#heading{align-items:center;bottom:0;display:flex;gap:.25rem;left:1rem;position:absolute;top:0}#heading>.toolbar{margin-left:-.75rem}#heading .dropmenu-btn>.text{max-width:142px}#heading>[data-zui-dropmenu]+div .dropmenu-btn>.text,#heading>[data-zui-dropmenu]+div+div .dropmenu-btn>.text{max-width:78px}#navbar{align-items:center;display:flex;font-size:.875rem;height:100%;justify-content:center;line-height:1.3rem;--state-color:rgba(var(--color-primary-500-rgb),.05);--state-active-opacity:1;--state-active-color:rgba(var(--color-primary-500-rgb),.08)}#navbar>.nav{--nav-active-color:var(--zt-navbar-active-color,var(--color-current));--nav-item-padding:12px;--nav-divider-margin:8px;margin-left:var(--nav-offset-left)}#navbar>.nav>.nav-item>a{height:3rem;padding-left:var(--nav-item-padding);padding-right:var(--nav-item-padding)}#navbar>.nav>.nav-item>a:before{--tw-scale-x:1!important;--tw-scale-y:1!important;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))!important;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color)!important;--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)!important;box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)!important}#navbar>.nav>.nav-item>a.active:before{background:var(--state-active-color)!important;opacity:1!important}#navbar>.nav>.divider{align-self:center;height:1.25rem;margin-left:var(--nav-divider-margin);margin-right:var(--nav-divider-margin);opacity:.2}#navbar>.nav.compact{font-size:.8125rem;line-height:1.25rem}#navbar>.nav.compact-extra{font-size:.75rem;line-height:1rem}#toolbar{align-items:center;bottom:0;display:flex;gap:.25rem;position:absolute;right:1rem;top:0}#main{min-height:100vh}#header+#main{min-height:calc(100vh - 3rem)}#main>.container{padding-left:1rem;padding-right:1rem;position:relative}@media (min-width:1400px){#header>.container,#main>.container,#mainNavbar>.container{padding-left:2.5rem;padding-right:2.5rem}#heading{left:2.5rem}#toolbar{right:2.5rem}}#mainNavbar{height:2.75rem;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}#mainNavbar>.container{position:relative}#mainNavbar .nav{bottom:0;height:2.75rem;justify-content:center;left:0;position:absolute;right:0;top:0}#mainNavbar .nav-item{font-size:.875rem;line-height:1.3rem}#mainNavbar .nav-item>a{border-radius:var(--radius)}#mainMenu{gap:1rem;justify-content:space-between;padding-bottom:.75rem;padding-top:.75rem}#featureBar,#mainMenu{align-items:center;display:flex}#featureBar{flex:1 1 auto;gap:.5rem}#actionBar{gap:.5rem}#actionBar>.nav-divider{margin-left:-.25rem;margin-right:-.25rem}#mainContent{padding-top:.75rem}#mainMenu+#mainContent{padding-top:0}#mainContent.row{align-items:stretch;display:flex;gap:1rem;justify-content:space-between}#mainContent.row>*{flex:1 1 auto;min-width:0}#mainContainer.has-sidebar-left{--gutter-left-size:16px}#mainContainer.is-sidebar-left-collapsed{--gutter-left-size:0}.has-sidebar-animation.has-sidebar-left #mainMenu{transition-duration:.15s;transition-property:padding-left;transition-timing-function:cubic-bezier(.4,0,.2,1)}:root{--modal-radius:var(--radius);--avatar-bg:var(--color-gray-200)}.modal-alert .modal-footer{justify-content:center}.modal-dialog{--tw-bg-opacity:1}.modal-content,.modal-dialog{max-height:calc(100vh - 4rem)}.modal-body,.modal-footer,.modal-header{padding:1.5rem 2rem}.modal-header{padding-right:3rem}.modal-body+.modal-footer,.modal-header+.modal-actions+.modal-body,.modal-header+.modal-body{padding-top:1px}.modal-condensed .modal-body,.modal-condensed .modal-header{padding:1rem 1.25rem}.modal-condensed .modal-actions{top:.75rem}:root{--label-bg:var(--color-gray-100);--label-color:var(--color-gray-800)}.label[class$=-pale],.label[class*="-pale "]{--tw-bg-opacity:0.4;--tw-ring-opacity:0.4}.body-modal .panel-form,.modal-body>.panel-form{margin:0;padding:0}.modal-body>.panel-form>.panel-heading{padding-left:1px;padding-right:1px;padding-top:1px}.modal-body>.panel-form>.panel-body{padding:1px}.modal-body>.form{padding-top:1px}.modal .history,.modal .panel-body>.form{padding:0}:root{--article-p-space:0}.lane-col-join-with-above{position:relative}.lane-col-join-with-above:before{background-color:inherit;left:0;position:absolute;right:0;--tw-content:"";content:var(--tw-content);height:var(--kanban-col-gap-top,var(--kanban-lanes-gap));top:calc(0px - var(--kanban-col-gap-top, var(--kanban-lanes-gap)))}.arrow,.arrow:before{background:inherit;height:calc(var(--arrow-size)*1.4142);position:absolute;width:calc(var(--arrow-size)*1.4142)}.arrow{visibility:hidden;--arrow-size:5px}.arrow:before{border:inherit;content:"";visibility:visible;--tw-rotate:45deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.arrow-top,.arrow-up{border-bottom:inherit;border-right:inherit;border-width:1px 0 0 1px;top:calc(1px - var(--arrow-size))}.white>.arrow-top,.white>.arrow-up{top:calc(0px - var(--arrow-size))}.arrow-bottom,.arrow-down{border-left:inherit;border-top:inherit;border-width:0 1px 1px 0;bottom:calc(1px - var(--arrow-size))}.white>.arrow-bottom,.white>.arrow-down{bottom:calc(0px - var(--arrow-size))}.arrow-left{border-right:inherit;border-top:inherit;border-width:0 0 1px 1px;left:calc(1px - var(--arrow-size))}.white>.arrow-left{left:calc(0px - var(--arrow-size))}.arrow-right{border-bottom:inherit;border-left:inherit;border-width:1px 1px 0 0;right:calc(1px - var(--arrow-size))}.white>.arrow-right{right:calc(0px - var(--arrow-size))}.caret,.caret-down,.caret-left,.caret-right,.caret-up{align-items:center;display:inline-flex;height:.75rem;justify-content:center;position:relative;width:.75rem}.caret-down:before,.caret-left:before,.caret-right:before,.caret-up:before,.caret:before{display:block;height:.35rem;transform-origin:center;width:.35rem;--tw-translate-y:-1px;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.caret-left:before{--tw-translate-x:0.125rem;--tw-translate-y:0px;--tw-rotate:135deg}.caret-left:before,.caret-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.caret-right:before{--tw-translate-x:-0.125rem;--tw-translate-y:0px;--tw-rotate:-45deg}.caret-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:focus>.caret,:hover>.caret{opacity:inherit}.disabled .caret,.readonly .caret{opacity:var(--caret-opacity,.5)}:root{--toggle-icon-size:calc(var(--font-size-root)*3/4 + 1px)}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-color:currentColor;border-width:1px;display:block;opacity:.5;position:relative}.toggle-icon-collapse:hover,.toggle-icon-expand:hover,.toggle-icon:hover{opacity:.9}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-radius:inherit;height:var(--toggle-icon-size);width:var(--toggle-icon-size)}.is-collapsed .toggle-icon:after,.is-collapsed .toggle-icon:before,.is-expanded .toggle-icon:before,.toggle-icon-collapse:after,.toggle-icon-collapse:before,.toggle-icon-expand:before{background-color:currentColor;content:" ";display:block;height:1px;left:2px;position:absolute;right:2px;top:calc((var(--toggle-icon-size) - 3px)/2)}.is-collapsed .toggle-icon:after,.toggle-icon-collapse:after{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.spinner,.spinner:after,.spinner:before{display:block;height:1em;position:relative;width:1em}.spinner:after,.spinner:before{border-radius:var(--radius-full);content:" ";position:absolute}.spinner:before{animation:-spin 1s cubic-bezier(.6,0,.4,1) infinite;border:.16667em solid transparent;border-top-color:currentcolor}.spinner:after{border:.16667em solid;opacity:.2}.magnifier{display:inline-block;height:1em;position:relative;width:1em}.magnifier:after,.magnifier:before{border-radius:var(--radius-full);content:"";display:block;position:absolute}.magnifier:before{border:1px solid;height:.75em;width:.75em}.magnifier:after{height:1px;left:.55em;top:.7em;width:.5em;--tw-rotate:45deg;background-color:currentColor;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.more,.more-vert{margin:.5rem;position:relative}.more,.more-vert,.more-vert:after,.more-vert:before,.more:after,.more:before{background-color:currentColor;border-radius:var(--radius-full);height:.125rem;width:.125rem}.more-vert:after,.more-vert:before,.more:after,.more:before{display:block;left:-5px;position:absolute;top:0;--tw-content:"";content:var(--tw-content)}.more-vert:after,.more:after{left:5px}.more-vert{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-down,.chevron-left,.chevron-right,.chevron-up{align-items:center;display:inline-flex;height:1em;justify-content:center;position:relative;width:1em}.chevron-down:before,.chevron-left:before,.chevron-right:before,.chevron-up:before{display:block;height:.6923077em;transform-origin:center;width:.6923077em;--tw-translate-y:-0.125rem;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.chevron-left:before{--tw-translate-y:0px;--tw-translate-x:0.125rem;--tw-rotate:135deg}.chevron-left:before,.chevron-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-right:before{--tw-translate-y:0px;--tw-translate-x:-0.125rem;--tw-rotate:-45deg}.chevron-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.i-time{border-color:currentColor;border-radius:50%;border-width:.08em;display:inline-block;height:1em;position:relative;width:1em}.i-time:after{border-color:currentColor;border-width:0 0 .08em .08em;height:.385em;left:.3846em;position:absolute;top:.08em;width:.385em;--tw-content:"";content:var(--tw-content)}.i-calendar{border-color:currentColor;border-radius:2px;border-width:.08em;display:inline-block;height:.79em;margin-top:.16em;position:relative;width:1em}.i-calendar:after,.i-calendar:before{border-color:currentColor;border-width:.08em;position:absolute;--tw-content:"";content:var(--tw-content)}.i-calendar:before{border-bottom-width:0;left:.15em;top:.307em;width:.6em}.i-calendar:after{border-bottom-width:0;border-top-width:0;height:.3077em;left:.17em;top:-.154em;width:.538em}:root{--state-color:rgba(0,0,0,.05);--state-scale:.9;--opacity-disabled:.7;--opacity-muted:.5;--load-indicator-duration:300ms;--load-indicator-delay:.5s}.btn,.item>a,.state{cursor:pointer;position:relative}.btn:before,.item>a:before,.state:before{background:var(--state-color);border-radius:inherit;bottom:0;content:" ";display:block;left:0;opacity:0;pointer-events:none;position:absolute;right:0;top:0;transform:scale(var(--state-scale));transition-duration:.2s;transition-property:opacity,transform,box-shadow,background-color;transition-timing-function:cubic-bezier(.4,0,.2,1)}.btn.active:not(:hover,:focus-visible,:focus-within,:active):before,.item>a.active:not(:hover,:focus-visible,:focus-within,:active):before,.state.active:not(:hover,:focus-visible,:focus-within,:active):before{background:var(--state-active-color,var(--state-color));opacity:var(--state-active-opacity,0);--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);transition-duration:.7s}.btn.selected:not(:hover,:focus-visible,:focus-within,:active):before,.item>a.selected:not(:hover,:focus-visible,:focus-within,:active):before,.state.selected:not(:hover,:focus-visible,:focus-within,:active):before{background:var(--state-selected-color,var(--state-scale));opacity:var(--state-selected-opacity,.1);--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.btn:focus-visible,.item>a:focus-visible,.state:focus-visible{outline:2px solid transparent;outline-offset:2px}.btn:active:before,.btn:focus-visible:before,.btn:hover:before,.item>a:active:before,.item>a:focus-visible:before,.item>a:hover:before,.state:active:before,.state:focus-visible:before,.state:hover:before{--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.btn:hover:before,.item>a:hover:before,.state:hover:before{opacity:var(--state-hover-opacity,1)}.btn:active:before,.item>a:active:before,.state:active:before{background:var(--state-pressed-color,var(--state-color));opacity:var(--state-pressed-opacity,.6);--tw-ring-color:var(--state-ring-color,currentColor);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);transition-duration:.7s}.btn:focus-visible:before,.item>a:focus-visible:before,.state:focus-visible:before{background:var(--state-focus-color,var(--state-color));opacity:var(--state-focus-opacity,1);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-focus-rgb),var(--tw-ring-opacity))}.btn.disabled:before,.btn[disabled]:before,.item>a.disabled:before,.item>a[disabled]:before,.state.disabled:before,.state[disabled]:before{display:none}.btn{--state-active-opacity:1}@-moz-document url-prefix(){.btn,:root{--state-active-opacity:0;--state-focus-opacity:0}}.disabled,.disabled *,[disabled],[disabled] *{cursor:not-allowed!important;opacity:var(--opacity-disabled);--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.load-indicator:after,.load-indicator:before{display:block;opacity:0;position:absolute;transition-delay:0s;transition-duration:.15s;transition-duration:var(--load-indicator-duration);transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);visibility:hidden}.load-indicator:before{align-items:center;background-color:rgba(var(--color-canvas-rgb),.7);border-radius:inherit;bottom:0;display:flex;font-size:.75rem;justify-content:center;left:0;line-height:1rem;right:0;top:0;z-index:99;--tw-content:attr(data-loading);content:var(--tw-content)}.load-indicator[data-loading]:before{padding-top:3.5rem}.load-indicator:after{border-color:transparent currentcolor currentcolor;border-radius:var(--radius-full);border-style:dotted;border-width:4px 3px 4px 4px;height:2rem;left:50%;margin-left:-1rem;margin-top:-1rem;top:50%;width:2rem;z-index:100;--tw-content:"";content:var(--tw-content)}.load-indicator.loading:after,.load-indicator.loading:before{opacity:1;transition-delay:var(--load-indicator-delay);visibility:visible}@keyframes -spin{to{transform:rotate(1turn)}}.load-indicator.loading:after{animation:-spin 1s linear infinite;opacity:.5}.events-none,.pointer-events-none{pointer-events:none}.events-auto,.pointer-events-auto{pointer-events:auto}.scroll-auto{scroll-behavior:auto}.scroll-smooth{scroll-behavior:smooth}.select-none{-webkit-user-select:none;-moz-user-select:none;user-select:none}.select-text{-webkit-user-select:text;-moz-user-select:text;user-select:text}.select-all{-webkit-user-select:all;-moz-user-select:all;user-select:all}.select-auto{-webkit-user-select:auto;-moz-user-select:auto;user-select:auto}.cursor-auto{cursor:auto}.cursor-default{cursor:default}.cursor-pointer{cursor:pointer}.cursor-wait{cursor:wait}.cursor-text{cursor:text}.cursor-move{cursor:move}.cursor-help{cursor:help}.cursor-not-allowed{cursor:not-allowed}.active\:opacity-100.active,.active\:opacity-100:active,.group.active .group-active\:opacity-100,.group:active .group-active\:opacity-100,.group:hover .group-hover\:opacity-100,.hover\:opacity-100:hover{opacity:1}.active\:opacity-0.active,.active\:opacity-0:active,.group.active .group-active\:opacity-0,.group:active .group-active\:opacity-0,.group:hover .group-hover\:opacity-0,.hover\:opacity-0:hover{opacity:0}.active\:text-primary.active,.active\:text-primary:active,.group.active .group-active\:text-primary,.group:active .group-active\:text-primary,.group:hover .group-hover\:text-primary,.hover\:text-primary:hover{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.active\:border-primary.active,.active\:border-primary:active,.group.active .group-active\:border-primary,.group:active .group-active\:border-primary,.group:hover .group-hover\:border-primary,.hover\:border-primary:hover{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity))}.active\:primary-pale.active,.active\:primary-pale:active,.group.active .group-active\:primary-pale,.group:active .group-active\:primary-pale,.group:hover .group-hover\:primary-pale,.hover\:primary-pale:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.active\:primary.active,.active\:primary:active,.group.active .group-active\:primary,.group:active .group-active\:primary,.group:hover .group-hover\:primary,.hover\:primary:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.active\:canvas.active,.active\:canvas:active,.group.active .group-active\:canvas,.group:active .group-active\:canvas,.group:hover .group-hover\:canvas,.hover\:canvas:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.active\:font-bold.active,.active\:font-bold:active,.group.active .group-active\:font-bold,.group:active .group-active\:font-bold,.group:hover .group-hover\:font-bold,.hover\:font-bold:hover{font-weight:700}.active\:shadow.active,.active\:shadow:active,.group.active .group-active\:shadow,.group:active .group-active\:shadow,.group:hover .group-hover\:shadow,.hover\:shadow:hover{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.group:hover .group-hover\:block,.hover\:block:hover{display:block!important}.group:hover .group-hover\:flex,.hover\:flex:hover{display:flex!important}.group:hover .group-hover\:inline-flex,.hover\:inline-flex:hover{display:inline-flex!important}.aspect-auto{aspect-ratio:auto}.aspect-square{aspect-ratio:1/1}.aspect-video{aspect-ratio:16/9}.container{width:100%}@media (min-width:1720px){.container{max-width:1720px}}.container{margin-left:auto;margin-right:auto}.popup{background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));border-radius:var(--radius);--tw-bg-opacity:0.85;--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;--tw-backdrop-blur:blur(16px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.block{display:block}.inline-block{display:inline-block}.inline{display:inline}.flex{display:flex}.inline-flex{display:inline-flex}.table{display:table}.table-cell{display:table-cell}.table-row{display:table-row}.hidden{display:none!important}.pull-right{float:right}.pull-left{float:left}.clearfix:after{clear:both;content:"";display:block}.object-contain{-o-object-fit:contain;object-fit:contain}.object-cover{-o-object-fit:cover;object-fit:cover}.object-fill{-o-object-fit:fill;object-fit:fill}.object-none{-o-object-fit:none;object-fit:none}.object-scale-down{-o-object-fit:scale-down;object-fit:scale-down}.object-bottom{-o-object-position:bottom;object-position:bottom}.object-center{-o-object-position:center;object-position:center}.object-left{-o-object-position:left;object-position:left}.object-left-bottom{-o-object-position:left bottom;object-position:left bottom}.object-left-top{-o-object-position:left top;object-position:left top}.object-right{-o-object-position:right;object-position:right}.object-right-bottom{-o-object-position:right bottom;object-position:right bottom}.object-right-top{-o-object-position:right top;object-position:right top}.object-top{-o-object-position:top;object-position:top}.overflow-auto{overflow:auto}.overflow-hidden{overflow:hidden}.overflow-clip{overflow:clip}.overflow-visible{overflow:visible}.overflow-scroll{overflow:scroll}.overflow-x-auto{overflow-x:auto}.overflow-y-auto{overflow-y:auto}.overflow-x-hidden{overflow-x:hidden}.overflow-y-hidden{overflow-y:hidden}.overflow-x-clip{overflow-x:clip}.overflow-y-clip{overflow-y:clip}.overflow-x-visible{overflow-x:visible}.overflow-y-visible{overflow-y:visible}.overflow-x-scroll{overflow-x:scroll}.overflow-y-scroll{overflow-y:scroll}.overflow-overlay{overflow:overlay}.static{position:static}.fixed{position:fixed}.absolute{position:absolute}.relative{position:relative}.sticky{position:sticky}.inset-0{bottom:0;left:0;right:0;top:0}.inset-auto{bottom:auto;left:auto;right:auto;top:auto}.inset-x-0{left:0;right:0}.inset-y-0{bottom:0;top:0}.top-0{top:0}.right-0{right:0}.bottom-0{bottom:0}.left-0{left:0}.top-full{top:100%}.right-full{right:100%}.bottom-full{bottom:100%}.left-full{left:100%}.top-auto{top:auto}.right-auto{right:auto}.bottom-auto{bottom:auto}.left-auto{left:auto}.top-px{top:1px}.right-px{right:1px}.bottom-px{bottom:1px}.left-px{left:1px}.top-0\.5{top:.125rem}.right-0\.5{right:.125rem}.bottom-0\.5{bottom:.125rem}.left-0\.5{left:.125rem}.top-1{top:.25rem}.right-1{right:.25rem}.bottom-1{bottom:.25rem}.left-1{left:.25rem}.top-1\.5{top:.375rem}.right-1\.5{right:.375rem}.bottom-1\.5{bottom:.375rem}.left-1\.5{left:.375rem}.top-2{top:.5rem}.right-2{right:.5rem}.bottom-2{bottom:.5rem}.left-2{left:.5rem}.top-2\.5{top:.625rem}.right-2\.5{right:.625rem}.bottom-2\.5{bottom:.625rem}.left-2\.5{left:.625rem}.top-3{top:.75rem}.right-3{right:.75rem}.bottom-3{bottom:.75rem}.left-3{left:.75rem}.top-3\.5{top:.875rem}.right-3\.5{right:.875rem}.bottom-3\.5{bottom:.875rem}.left-3\.5{left:.875rem}.top-4{top:1rem}.right-4{right:1rem}.bottom-4{bottom:1rem}.left-4{left:1rem}.top-5{top:1.25rem}.right-5{right:1.25rem}.bottom-5{bottom:1.25rem}.left-5{left:1.25rem}.top-6{top:1.5rem}.right-6{right:1.5rem}.bottom-6{bottom:1.5rem}.left-6{left:1.5rem}.top-7{top:1.75rem}.right-7{right:1.75rem}.bottom-7{bottom:1.75rem}.left-7{left:1.75rem}.top-8{top:2rem}.right-8{right:2rem}.bottom-8{bottom:2rem}.left-8{left:2rem}.visible{visibility:visible!important}.invisible{visibility:hidden!important}.z-0{z-index:0}.z-1{z-index:1}.z-5{z-index:5}.z-10{z-index:10}.z-20{z-index:20}.z-30{z-index:30}.z-40{z-index:40}.z-50{z-index:50}.z-auto{z-index:auto}.z-base{z-index:1100}.z-above{z-index:50}.z-below{z-index:-50}.z-dropdown{z-index:1200}.z-sticky{z-index:1300}.z-fixed{z-index:1400}.z-modal{z-index:1500}.z-overlay{z-index:1600}.z-popover{z-index:1700}.z-tooltip{z-index:1800}.z-messager{z-index:1900}.m-0{margin:0}.m-auto{margin:auto}.m-px{margin:1px}.m-0\.5{margin:.125rem}.m-1{margin:.25rem}.m-1\.5{margin:.375rem}.m-2{margin:.5rem}.m-2\.5{margin:.625rem}.m-3{margin:.75rem}.m-3\.5{margin:.875rem}.m-4{margin:1rem}.m-5{margin:1.25rem}.m-6{margin:1.5rem}.m-7{margin:1.75rem}.m-8{margin:2rem}.m-9{margin:2.25rem}.m-10{margin:2.5rem}.mx-0{margin-left:0;margin-right:0}.my-0{margin-bottom:0}.mt-0,.my-0{margin-top:0}.mr-0{margin-right:0}.mb-0{margin-bottom:0}.ml-0{margin-left:0}.mx-auto{margin-left:auto;margin-right:auto}.my-auto{margin-bottom:auto}.mt-auto,.my-auto{margin-top:auto}.mr-auto{margin-right:auto}.mb-auto{margin-bottom:auto}.ml-auto{margin-left:auto}.mx-px{margin-left:1px;margin-right:1px}.my-px{margin-bottom:1px}.mt-px,.my-px{margin-top:1px}.mr-px{margin-right:1px}.mb-px{margin-bottom:1px}.ml-px{margin-left:1px}.mx-0\.5{margin-left:.125rem;margin-right:.125rem}.my-0\.5{margin-bottom:.125rem}.mt-0\.5,.my-0\.5{margin-top:.125rem}.mr-0\.5{margin-right:.125rem}.mb-0\.5{margin-bottom:.125rem}.ml-0\.5{margin-left:.125rem}.mx-1{margin-left:.25rem;margin-right:.25rem}.my-1{margin-bottom:.25rem}.mt-1,.my-1{margin-top:.25rem}.mr-1{margin-right:.25rem}.mb-1{margin-bottom:.25rem}.ml-1{margin-left:.25rem}.mx-1\.5{margin-left:.375rem;margin-right:.375rem}.my-1\.5{margin-bottom:.375rem}.mt-1\.5,.my-1\.5{margin-top:.375rem}.mr-1\.5{margin-right:.375rem}.mb-1\.5{margin-bottom:.375rem}.ml-1\.5{margin-left:.375rem}.mx-2{margin-left:.5rem;margin-right:.5rem}.my-2{margin-bottom:.5rem}.mt-2,.my-2{margin-top:.5rem}.mr-2{margin-right:.5rem}.mb-2{margin-bottom:.5rem}.ml-2{margin-left:.5rem}.mx-2\.5{margin-left:.625rem;margin-right:.625rem}.my-2\.5{margin-bottom:.625rem}.mt-2\.5,.my-2\.5{margin-top:.625rem}.mr-2\.5{margin-right:.625rem}.mb-2\.5{margin-bottom:.625rem}.ml-2\.5{margin-left:.625rem}.mx-3{margin-left:.75rem;margin-right:.75rem}.my-3{margin-bottom:.75rem}.mt-3,.my-3{margin-top:.75rem}.mr-3{margin-right:.75rem}.mb-3{margin-bottom:.75rem}.ml-3{margin-left:.75rem}.mx-3\.5{margin-left:.875rem;margin-right:.875rem}.my-3\.5{margin-bottom:.875rem}.mt-3\.5,.my-3\.5{margin-top:.875rem}.mr-3\.5{margin-right:.875rem}.mb-3\.5{margin-bottom:.875rem}.ml-3\.5{margin-left:.875rem}.mx-4{margin-left:1rem;margin-right:1rem}.my-4{margin-bottom:1rem}.mt-4,.my-4{margin-top:1rem}.mr-4{margin-right:1rem}.mb-4{margin-bottom:1rem}.ml-4{margin-left:1rem}.mx-5{margin-left:1.25rem;margin-right:1.25rem}.my-5{margin-bottom:1.25rem}.mt-5,.my-5{margin-top:1.25rem}.mr-5{margin-right:1.25rem}.mb-5{margin-bottom:1.25rem}.ml-5{margin-left:1.25rem}.mx-6{margin-left:1.5rem;margin-right:1.5rem}.my-6{margin-bottom:1.5rem}.mt-6,.my-6{margin-top:1.5rem}.mr-6{margin-right:1.5rem}.mb-6{margin-bottom:1.5rem}.ml-6{margin-left:1.5rem}.mx-7{margin-left:1.75rem;margin-right:1.75rem}.my-7{margin-bottom:1.75rem}.mt-7,.my-7{margin-top:1.75rem}.mr-7{margin-right:1.75rem}.mb-7{margin-bottom:1.75rem}.ml-7{margin-left:1.75rem}.mx-8{margin-left:2rem;margin-right:2rem}.my-8{margin-bottom:2rem}.mt-8,.my-8{margin-top:2rem}.mr-8{margin-right:2rem}.mb-8{margin-bottom:2rem}.ml-8{margin-left:2rem}.mx-9{margin-left:2.25rem;margin-right:2.25rem}.my-9{margin-bottom:2.25rem}.mt-9,.my-9{margin-top:2.25rem}.mr-9{margin-right:2.25rem}.mb-9{margin-bottom:2.25rem}.ml-9{margin-left:2.25rem}.mx-10{margin-left:2.5rem;margin-right:2.5rem}.my-10{margin-bottom:2.5rem}.mt-10,.my-10{margin-top:2.5rem}.mr-10{margin-right:2.5rem}.mb-10{margin-bottom:2.5rem}.ml-10{margin-left:2.5rem}.p-0{padding:0}.p-px{padding:1px}.p-0\.5{padding:.125rem}.p-1{padding:.25rem}.p-1\.5{padding:.375rem}.p-2{padding:.5rem}.p-2\.5{padding:.625rem}.p-3{padding:.75rem}.p-3\.5{padding:.875rem}.p-4{padding:1rem}.p-5{padding:1.25rem}.p-6{padding:1.5rem}.p-7{padding:1.75rem}.p-8{padding:2rem}.p-9{padding:2.25rem}.p-10{padding:2.5rem}.px-0{padding-left:0;padding-right:0}.py-0{padding-bottom:0}.pt-0,.py-0{padding-top:0}.pr-0{padding-right:0}.pb-0{padding-bottom:0}.pl-0{padding-left:0}.px-px{padding-left:1px;padding-right:1px}.py-px{padding-bottom:1px}.pt-px,.py-px{padding-top:1px}.pr-px{padding-right:1px}.pb-px{padding-bottom:1px}.pl-px{padding-left:1px}.px-0\.5{padding-left:.125rem;padding-right:.125rem}.py-0\.5{padding-bottom:.125rem}.pt-0\.5,.py-0\.5{padding-top:.125rem}.pr-0\.5{padding-right:.125rem}.pb-0\.5{padding-bottom:.125rem}.pl-0\.5{padding-left:.125rem}.px-1{padding-left:.25rem;padding-right:.25rem}.py-1{padding-bottom:.25rem}.pt-1,.py-1{padding-top:.25rem}.pr-1{padding-right:.25rem}.pb-1{padding-bottom:.25rem}.pl-1{padding-left:.25rem}.px-1\.5{padding-left:.375rem;padding-right:.375rem}.py-1\.5{padding-bottom:.375rem}.pt-1\.5,.py-1\.5{padding-top:.375rem}.pr-1\.5{padding-right:.375rem}.pb-1\.5{padding-bottom:.375rem}.pl-1\.5{padding-left:.375rem}.px-2{padding-left:.5rem;padding-right:.5rem}.py-2{padding-bottom:.5rem}.pt-2,.py-2{padding-top:.5rem}.pr-2{padding-right:.5rem}.pb-2{padding-bottom:.5rem}.pl-2{padding-left:.5rem}.px-2\.5{padding-left:.625rem;padding-right:.625rem}.py-2\.5{padding-bottom:.625rem}.pt-2\.5,.py-2\.5{padding-top:.625rem}.pr-2\.5{padding-right:.625rem}.pb-2\.5{padding-bottom:.625rem}.pl-2\.5{padding-left:.625rem}.px-3{padding-left:.75rem;padding-right:.75rem}.py-3{padding-bottom:.75rem}.pt-3,.py-3{padding-top:.75rem}.pr-3{padding-right:.75rem}.pb-3{padding-bottom:.75rem}.pl-3{padding-left:.75rem}.px-3\.5{padding-left:.875rem;padding-right:.875rem}.py-3\.5{padding-bottom:.875rem}.pt-3\.5,.py-3\.5{padding-top:.875rem}.pr-3\.5{padding-right:.875rem}.pb-3\.5{padding-bottom:.875rem}.pl-3\.5{padding-left:.875rem}.px-4{padding-left:1rem;padding-right:1rem}.py-4{padding-bottom:1rem}.pt-4,.py-4{padding-top:1rem}.pr-4{padding-right:1rem}.pb-4{padding-bottom:1rem}.pl-4{padding-left:1rem}.px-5{padding-left:1.25rem;padding-right:1.25rem}.py-5{padding-bottom:1.25rem}.pt-5,.py-5{padding-top:1.25rem}.pr-5{padding-right:1.25rem}.pb-5{padding-bottom:1.25rem}.pl-5{padding-left:1.25rem}.px-6{padding-left:1.5rem;padding-right:1.5rem}.py-6{padding-bottom:1.5rem}.pt-6,.py-6{padding-top:1.5rem}.pr-6{padding-right:1.5rem}.pb-6{padding-bottom:1.5rem}.pl-6{padding-left:1.5rem}.px-7{padding-left:1.75rem;padding-right:1.75rem}.py-7{padding-bottom:1.75rem}.pt-7,.py-7{padding-top:1.75rem}.pr-7{padding-right:1.75rem}.pb-7{padding-bottom:1.75rem}.pl-7{padding-left:1.75rem}.px-8{padding-left:2rem;padding-right:2rem}.py-8{padding-bottom:2rem}.pt-8,.py-8{padding-top:2rem}.pr-8{padding-right:2rem}.pb-8{padding-bottom:2rem}.pl-8{padding-left:2rem}.px-9{padding-left:2.25rem;padding-right:2.25rem}.py-9{padding-bottom:2.25rem}.pt-9,.py-9{padding-top:2.25rem}.pr-9{padding-right:2.25rem}.pb-9{padding-bottom:2.25rem}.pl-9{padding-left:2.25rem}.px-10{padding-left:2.5rem;padding-right:2.5rem}.py-10{padding-bottom:2.5rem}.pt-10,.py-10{padding-top:2.5rem}.pr-10{padding-right:2.5rem}.pb-10{padding-bottom:2.5rem}.pl-10{padding-left:2.5rem}.space-x-0>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(0px*(1 - var(--tw-space-x-reverse)));margin-right:calc(0px*var(--tw-space-x-reverse))}.space-y-0>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(0px*var(--tw-space-y-reverse));margin-top:calc(0px*(1 - var(--tw-space-y-reverse)))}.space-x-0\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.125rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.125rem*var(--tw-space-x-reverse))}.space-y-0\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.125rem*var(--tw-space-y-reverse));margin-top:calc(.125rem*(1 - var(--tw-space-y-reverse)))}.space-x-1>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}.space-y-1>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.25rem*var(--tw-space-y-reverse));margin-top:calc(.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-1\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.375rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.375rem*var(--tw-space-x-reverse))}.space-y-1\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.375rem*var(--tw-space-y-reverse));margin-top:calc(.375rem*(1 - var(--tw-space-y-reverse)))}.space-x-2>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.5rem*var(--tw-space-x-reverse))}.space-y-2>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-2\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.625rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.625rem*var(--tw-space-x-reverse))}.space-y-2\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.625rem*var(--tw-space-y-reverse));margin-top:calc(.625rem*(1 - var(--tw-space-y-reverse)))}.space-x-3>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.75rem*var(--tw-space-x-reverse))}.space-y-3>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.75rem*var(--tw-space-y-reverse));margin-top:calc(.75rem*(1 - var(--tw-space-y-reverse)))}.space-x-3\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.875rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.875rem*var(--tw-space-x-reverse))}.space-y-3\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.875rem*var(--tw-space-y-reverse));margin-top:calc(.875rem*(1 - var(--tw-space-y-reverse)))}.space-x-4>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1rem*var(--tw-space-x-reverse))}.space-y-4>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.space-x-5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.25rem*var(--tw-space-x-reverse))}.space-y-5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.25rem*var(--tw-space-y-reverse));margin-top:calc(1.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-6>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.5rem*var(--tw-space-x-reverse))}.space-y-6>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.5rem*var(--tw-space-y-reverse));margin-top:calc(1.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-7>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.75rem*var(--tw-space-x-reverse))}.space-y-7>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.75rem*var(--tw-space-y-reverse));margin-top:calc(1.75rem*(1 - var(--tw-space-y-reverse)))}.space-x-8>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2rem*var(--tw-space-x-reverse))}.space-y-8>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2rem*var(--tw-space-y-reverse));margin-top:calc(2rem*(1 - var(--tw-space-y-reverse)))}.space-x-9>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2.25rem*var(--tw-space-x-reverse))}.space-y-9>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2.25rem*var(--tw-space-y-reverse));margin-top:calc(2.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-10>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2.5rem*var(--tw-space-x-reverse))}.space-y-10>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2.5rem*var(--tw-space-y-reverse));margin-top:calc(2.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1px*(1 - var(--tw-space-x-reverse)));margin-right:calc(1px*var(--tw-space-x-reverse))}.space-y-px>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1px*var(--tw-space-y-reverse));margin-top:calc(1px*(1 - var(--tw-space-y-reverse)))}.w-0{width:0}.w-px{width:1px}.w-0\.5{width:.125rem}.w-1{width:.25rem}.w-1\.5{width:.375rem}.w-2{width:.5rem}.w-2\.5{width:.625rem}.w-3{width:.75rem}.w-3\.5{width:.875rem}.w-4{width:1rem}.w-5{width:1.25rem}.w-6{width:1.5rem}.w-7{width:1.75rem}.w-8{width:2rem}.w-9{width:2.25rem}.w-10{width:2.5rem}.w-11{width:2.75rem}.w-12{width:3rem}.w-14{width:3.5rem}.w-16{width:4rem}.w-20{width:5rem}.w-24{width:6rem}.w-28{width:7rem}.w-32{width:8rem}.w-36{width:9rem}.w-40{width:10rem}.w-44{width:11rem}.w-48{width:12rem}.w-52{width:13rem}.w-56{width:14rem}.w-60{width:15rem}.w-64{width:16rem}.w-72{width:18rem}.w-80{width:20rem}.w-96{width:24rem}.w-1\/2{width:50%}.w-1\/3{width:33.333333%}.w-2\/3{width:66.666667%}.w-1\/4{width:25%}.w-2\/4{width:50%}.w-3\/4{width:75%}.w-1\/5{width:20%}.w-2\/5{width:40%}.w-3\/5{width:60%}.w-4\/5{width:80%}.w-1\/6{width:16.666667%}.w-2\/6{width:33.333333%}.w-3\/6{width:50%}.w-4\/6{width:66.666667%}.w-5\/6{width:83.333333%}.w-auto{width:auto}.w-full{width:100%}.w-screen{width:100vw}.w-min{width:-moz-min-content;width:min-content}.w-max{width:-moz-max-content;width:max-content}.w-fit{width:-moz-fit-content;width:fit-content}.min-w-0{min-width:0}.min-w-full{min-width:100%}.min-w-min{min-width:-moz-min-content;min-width:min-content}.min-w-max{min-width:-moz-max-content;min-width:max-content}.min-w-fit{min-width:-moz-fit-content;min-width:fit-content}.max-w-0{max-width:0}.max-w-none{max-width:none}.max-w-xs{max-width:20rem}.max-w-sm{max-width:24rem}.max-w-md{max-width:28rem}.max-w-lg{max-width:32rem}.max-w-xl{max-width:36rem}.max-w-2xl{max-width:42rem}.max-w-3xl{max-width:48rem}.max-w-4xl{max-width:56rem}.max-w-5xl{max-width:64rem}.max-w-6xl{max-width:72rem}.max-w-7xl{max-width:80rem}.max-w-full{max-width:100%}.max-w-min{max-width:-moz-min-content;max-width:min-content}.max-w-max{max-width:-moz-max-content;max-width:max-content}.max-w-fit{max-width:-moz-fit-content;max-width:fit-content}.h-0{height:0}.h-px{height:1px}.h-0\.5{height:.125rem}.h-1{height:.25rem}.h-1\.5{height:.375rem}.h-2{height:.5rem}.h-2\.5{height:.625rem}.h-3{height:.75rem}.h-3\.5{height:.875rem}.h-4{height:1rem}.h-5{height:1.25rem}.h-6{height:1.5rem}.h-7{height:1.75rem}.h-8{height:2rem}.h-9{height:2.25rem}.h-10{height:2.5rem}.h-11{height:2.75rem}.h-12{height:3rem}.h-14{height:3.5rem}.h-16{height:4rem}.h-20{height:5rem}.h-24{height:6rem}.h-28{height:7rem}.h-32{height:8rem}.h-36{height:9rem}.h-40{height:10rem}.h-44{height:11rem}.h-48{height:12rem}.h-52{height:13rem}.h-56{height:14rem}.h-60{height:15rem}.h-64{height:16rem}.h-72{height:18rem}.h-80{height:20rem}.h-96{height:24rem}.h-1\/2{height:50%}.h-1\/3{height:33.333333%}.h-2\/3{height:66.666667%}.h-1\/4{height:25%}.h-2\/4{height:50%}.h-3\/4{height:75%}.h-1\/5{height:20%}.h-2\/5{height:40%}.h-3\/5{height:60%}.h-4\/5{height:80%}.h-1\/6{height:16.666667%}.h-2\/6{height:33.333333%}.h-3\/6{height:50%}.h-4\/6{height:66.666667%}.h-5\/6{height:83.333333%}.h-auto{height:auto}.h-full{height:100%}.h-screen{height:100vh}.h-min{height:-moz-min-content;height:min-content}.h-max{height:-moz-max-content;height:max-content}.h-fit{height:-moz-fit-content;height:fit-content}.min-h-0{min-height:0}.min-h-full{min-height:100%}.min-h-min{min-height:-moz-min-content;min-height:min-content}.min-h-max{min-height:-moz-max-content;min-height:max-content}.min-h-fit{min-height:-moz-fit-content;min-height:fit-content}.max-h-0{max-height:0}.max-h-px{max-height:1px}.max-h-none{max-height:none}.max-h-full{max-height:100%}.max-h-min{max-height:-moz-min-content;max-height:min-content}.max-h-screen{max-height:100vh}.max-h-max{max-height:-moz-max-content;max-height:max-content}.max-h-fit{max-height:-moz-fit-content;max-height:fit-content}.canvas,.surface,.surface-light,.surface-strong{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}.canvas{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.surface-light{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-light-rgb),var(--tw-ring-opacity))}.surface{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-rgb),var(--tw-ring-opacity))}.surface-strong{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-strong-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-strong-rgb),var(--tw-ring-opacity))}.inverse{background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity));color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.inverse,.white{--tw-bg-opacity:1;--tw-text-opacity:1}.white{background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity));color:rgba(var(--color-fore-in-light-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-white-rgb),var(--tw-ring-opacity))}.black{--tw-bg-opacity:1;background-color:rgba(var(--color-black-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-black-rgb),var(--tw-ring-opacity))}.transparent{background-color:transparent;--tw-ring-color:transparent}.skin{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.skin:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger,.darken,.darker,.darkest,.gray,.gray-100,.gray-200,.gray-300,.gray-400,.gray-50,.gray-500,.gray-600,.gray-700,.gray-800,.gray-900,.gray-950,.important,.lighten,.lighter,.lightest,.primary,.secondary,.special,.success,.warning{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger:hover,.darken:hover,.darker:hover,.darkest:hover,.gray-100:hover,.gray-200:hover,.gray-300:hover,.gray-400:hover,.gray-500:hover,.gray-50:hover,.gray-600:hover,.gray-700:hover,.gray-800:hover,.gray-900:hover,.gray-950:hover,.gray:hover,.important:hover,.lighten:hover,.lighter:hover,.lightest:hover,.primary:hover,.secondary:hover,.special:hover,.success:hover,.warning:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger,.darken,.darker,.darkest,.gray,.gray-100,.gray-200,.gray-300,.gray-400,.gray-50,.gray-500,.gray-600,.gray-700,.gray-800,.gray-900,.gray-950,.important,.lighten,.lighter,.lightest,.primary,.secondary,.special,.success,.warning{--skin-text:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity));--skin-color:rgba(var(--skin-solid-rgb),1);--state-ring-color:var(--skin-color);--state-active-color:rgba(0,0,0,.1);--state-pressed-color:rgba(0,0,0,.1);--state-color:hsla(0,0%,100%,.1);--state-focus-color:rgba(0,0,0,.1)}.primary{--skin-solid-rgb:var(--color-primary-500-rgb)}.secondary{--skin-solid-rgb:var(--color-secondary-500-rgb)}.success{--skin-solid-rgb:var(--color-success-500-rgb)}.warning{--skin-solid-rgb:var(--color-warning-500-rgb)}.danger{--skin-solid-rgb:var(--color-danger-500-rgb)}.important{--skin-solid-rgb:var(--color-important-500-rgb)}.special{--skin-solid-rgb:var(--color-special-500-rgb)}.gray-50{--skin-bg:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity));--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-100{--skin-solid-rgb:var(--color-gray-100-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-200,.lightest{--skin-solid-rgb:var(--color-gray-200-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-300,.lighter{--skin-solid-rgb:var(--color-gray-300-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-400,.lighten{--skin-solid-rgb:var(--color-gray-400-rgb)}.gray,.gray-500{--skin-solid-rgb:var(--color-gray-500-rgb)}.darken,.gray-600{--skin-solid-rgb:var(--color-gray-600-rgb)}.darker,.gray-700{--skin-solid-rgb:var(--color-gray-700-rgb)}.darkest,.gray-800{--skin-solid-rgb:var(--color-gray-800-rgb)}.gray-900{--skin-solid-rgb:var(--color-gray-900-rgb)}.gray-950{--skin-solid-rgb:var(--color-gray-950-rgb)}.danger-pale,.gray-100-pale,.gray-200-pale,.gray-300-pale,.gray-400-pale,.gray-50-pale,.gray-500-pale,.gray-600-pale,.gray-700-pale,.gray-800-pale,.gray-900-pale,.gray-950-pale,.gray-pale,.important-pale,.pale,.primary-pale,.secondary-pale,.special-pale,.success-pale,.warning-pale{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-pale:hover,.gray-100-pale:hover,.gray-200-pale:hover,.gray-300-pale:hover,.gray-400-pale:hover,.gray-50-pale:hover,.gray-500-pale:hover,.gray-600-pale:hover,.gray-700-pale:hover,.gray-800-pale:hover,.gray-900-pale:hover,.gray-950-pale:hover,.gray-pale:hover,.important-pale:hover,.pale:hover,.primary-pale:hover,.secondary-pale:hover,.special-pale:hover,.success-pale:hover,.warning-pale:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-pale,.gray-100-pale,.gray-200-pale,.gray-300-pale,.gray-400-pale,.gray-50-pale,.gray-500-pale,.gray-600-pale,.gray-700-pale,.gray-800-pale,.gray-900-pale,.gray-950-pale,.gray-pale,.important-pale,.pale,.primary-pale,.secondary-pale,.special-pale,.success-pale,.warning-pale{--skin-color:rgba(var(--skin-pale-rgb),.1);--skin-text:rgba(var(--skin-pale-rgb),1);--state-color:rgba(var(--skin-pale-rgb),.1)}.pale{--skin-pale-rgb:var(--color-gray-500-rgb)}.primary-pale{--skin-pale-rgb:var(--color-primary-500-rgb)}.secondary-pale{--skin-pale-rgb:var(--color-secondary-500-rgb)}.success-pale{--skin-pale-rgb:var(--color-success-500-rgb)}.warning-pale{--skin-pale-rgb:var(--color-warning-500-rgb)}.danger-pale{--skin-pale-rgb:var(--color-danger-500-rgb)}.important-pale{--skin-pale-rgb:var(--color-important-500-rgb)}.special-pale{--skin-pale-rgb:var(--color-special-500-rgb)}.gray-50-pale{--skin-pale-rgb:var(--color-gray-50-rgb);--skin-text:var(--color-gray-400)}.gray-100-pale{--skin-pale-rgb:var(--color-gray-100-rgb);--skin-text:var(--color-gray-400)}.gray-200-pale{--skin-pale-rgb:var(--color-gray-200-rgb);--skin-text:var(--color-gray-400)}.gray-300-pale{--skin-pale-rgb:var(--color-gray-300-rgb);--skin-text:var(--color-gray-500)}.gray-400-pale{--skin-pale-rgb:var(--color-gray-400-rgb);--skin-text:var(--color-gray-500)}.gray-500-pale,.gray-pale{--skin-pale-rgb:var(--color-gray-500-rgb)}.gray-600-pale{--skin-pale-rgb:var(--color-gray-600-rgb)}.gray-700-pale{--skin-pale-rgb:var(--color-gray-700-rgb)}.gray-800-pale{--skin-pale-rgb:var(--color-gray-800-rgb)}.gray-900-pale{--skin-pale-rgb:var(--color-gray-900-rgb)}.gray-950-pale{--skin-pale-rgb:var(--color-gray-950-rgb)}.danger-outline,.dark-outline,.gray-300-outline,.gray-400-outline,.gray-600-outline,.gray-outline,.important-outline,.light-outline,.outline,.primary-outline,.secondary-outline,.special-outline,.success-outline,.warning-outline{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-outline:hover,.dark-outline:hover,.gray-300-outline:hover,.gray-400-outline:hover,.gray-600-outline:hover,.gray-outline:hover,.important-outline:hover,.light-outline:hover,.outline:hover,.primary-outline:hover,.secondary-outline:hover,.special-outline:hover,.success-outline:hover,.warning-outline:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-outline,.dark-outline,.gray-300-outline,.gray-400-outline,.gray-600-outline,.gray-outline,.important-outline,.light-outline,.outline,.primary-outline,.secondary-outline,.special-outline,.success-outline,.warning-outline{--skin-text:var(--skin-color,inherit);--skin-bg:transparent;--skin-color:rgba(var(--skin-outline-rgb),1);--state-color:rgba(var(--skin-outline-rgb),.1)}.outline{--skin-outline-rgb:var(--color-fore-rgb)}.primary-outline{--skin-outline-rgb:var(--color-primary-500-rgb)}.secondary-outline{--skin-outline-rgb:var(--color-secondary-500-rgb)}.success-outline{--skin-outline-rgb:var(--color-success-500-rgb)}.warning-outline{--skin-outline-rgb:var(--color-warning-500-rgb)}.danger-outline{--skin-outline-rgb:var(--color-danger-500-rgb)}.important-outline{--skin-outline-rgb:var(--color-important-500-rgb)}.special-outline{--skin-outline-rgb:var(--color-special-500-rgb)}.gray-300-outline{--skin-text:var(--color-gray-500);--skin-outline-rgb:var(--color-gray-300-rgb)}.gray-400-outline{--skin-text:var(--color-gray-500);--skin-outline-rgb:var(--color-gray-400-rgb)}.gray-outline{--skin-outline-rgb:var(--color-gray-500-rgb)}.gray-600-outline{--skin-outline-rgb:var(--color-gray-600-rgb)}.dark-outline{--skin-outline-rgb:var(--color-inverse-rgb)}.light-outline{--skin-outline-rgb:var(--color-canvas-rgb)}.danger-ghost,.ghost,.important-ghost,.primary-ghost,.secondary-ghost,.special-ghost,.success-ghost,.warning-ghost{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-ghost:hover,.ghost:hover,.important-ghost:hover,.primary-ghost:hover,.secondary-ghost:hover,.special-ghost:hover,.success-ghost:hover,.warning-ghost:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-ghost,.ghost,.important-ghost,.primary-ghost,.secondary-ghost,.special-ghost,.success-ghost,.warning-ghost{--tw-ring-opacity:0;--tw-bg-opacity:0;--skin-text:var(--skin-color,inherit);--skin-bg:transparent;--skin-ring:transparent;--skin-color:rgba(var(--skin-ghost-rgb),1);--state-color:rgba(var(--skin-ghost-rgb),.1)}.ghost{--skin-ghost-rgb:var(--color-fore-rgb);--skin-text:inherit}.primary-ghost{--skin-ghost-rgb:var(--color-primary-500-rgb)}.secondary-ghost{--skin-ghost-rgb:var(--color-secondary-500-rgb)}.success-ghost{--skin-ghost-rgb:var(--color-success-500-rgb)}.warning-ghost{--skin-ghost-rgb:var(--color-warning-500-rgb)}.danger-ghost{--skin-ghost-rgb:var(--color-danger-500-rgb)}.important-ghost{--skin-ghost-rgb:var(--color-important-500-rgb)}.special-ghost{--skin-ghost-rgb:var(--color-special-500-rgb)}.font-sans{font-family:-apple-system,Noto Sans,Helvetica Neue,Helvetica,Nimbus Sans L,Arial,Liberation Sans,PingFang SC,Hiragino Sans GB,Noto Sans CJK SC,Source Han Sans SC,Source Han Sans CN,Microsoft YaHei,Wenquanyi Micro Hei,WenQuanYi Zen Hei,ST Heiti,SimHei,WenQuanYi Zen Hei Sharp,sans-serif}.font-serif{font-family:Nimbus Roman No9 L,Songti SC,Noto Serif CJK SC,Source Han Serif SC,Source Han Serif CN,STSong,AR PL New Sung,AR PL SungtiL GB,NSimSun,SimSun,TW-Sung,WenQuanYi Bitmap Song,AR PL UMing CN,AR PL UMing HK,AR PL UMing TW,AR PL UMing TW MBE,PMingLiU,MingLiU,serif}.font-mono{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace}.text-root{font-size:16px}.text-sm{font-size:.75rem;line-height:1rem}.text-base{font-size:.8125rem;line-height:1.25rem}.text-md{font-size:.875rem;line-height:1.3rem}.text-lg{font-size:1rem;line-height:1.5rem}.text-xl{font-size:1.125rem;line-height:1.75rem}.text-2xl{font-size:1.5rem;line-height:2rem}.text-3xl{font-size:1.875rem;line-height:2.25rem}.text-4xl{font-size:2.25rem;line-height:2.5rem}.font-thin{font-weight:100}.font-light{font-weight:300}.font-normal{font-weight:400}.font-medium{font-weight:500}.font-semibold{font-weight:600}.font-bold{font-weight:700}.font-black{font-weight:900}.leading-3{line-height:.75rem}.leading-4{line-height:1rem}.leading-5{line-height:1.25rem}.leading-6{line-height:1.5rem}.leading-7{line-height:1.75rem}.leading-8{line-height:2rem}.leading-9{line-height:2.25rem}.leading-10{line-height:2.5rem}.leading-none{line-height:1}.leading-tight{line-height:1.25}.leading-snug{line-height:1.375}.leading-normal{line-height:1.5}.leading-relaxed{line-height:1.625}.leading-loose{line-height:2}.line-clamp-1{-webkit-line-clamp:1}.line-clamp-1,.line-clamp-2{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-2{-webkit-line-clamp:2}.line-clamp-3{-webkit-line-clamp:3}.line-clamp-3,.line-clamp-4{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-4{-webkit-line-clamp:4}.line-clamp-5{-webkit-line-clamp:5}.line-clamp-5,.line-clamp-6{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-6{-webkit-line-clamp:6}.text-left{text-align:left}.text-center{text-align:center}.text-right{text-align:right}.text-justify{text-align:justify}.align-middle{vertical-align:middle}.align-top{vertical-align:top}.align-bottom{vertical-align:bottom}.align-sub{vertical-align:sub}.align-super{vertical-align:super}.text-primary{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.text-secondary{--tw-text-opacity:1;color:rgba(var(--color-secondary-500-rgb),var(--tw-text-opacity))}.text-success{--tw-text-opacity:1;color:rgba(var(--color-success-500-rgb),var(--tw-text-opacity))}.text-warning{--tw-text-opacity:1;color:rgba(var(--color-warning-500-rgb),var(--tw-text-opacity))}.text-danger{--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.text-important{--tw-text-opacity:1;color:rgba(var(--color-important-500-rgb),var(--tw-text-opacity))}.text-special{--tw-text-opacity:1;color:rgba(var(--color-special-500-rgb),var(--tw-text-opacity))}.text-primary-50{--tw-text-opacity:1;color:rgba(var(--color-primary-50-rgb),var(--tw-text-opacity))}.text-primary-100{--tw-text-opacity:1;color:rgba(var(--color-primary-100-rgb),var(--tw-text-opacity))}.text-primary-200{--tw-text-opacity:1;color:rgba(var(--color-primary-200-rgb),var(--tw-text-opacity))}.text-primary-300{--tw-text-opacity:1;color:rgba(var(--color-primary-300-rgb),var(--tw-text-opacity))}.text-primary-400{--tw-text-opacity:1;color:rgba(var(--color-primary-400-rgb),var(--tw-text-opacity))}.text-primary-500{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.text-primary-600{--tw-text-opacity:1;color:rgba(var(--color-primary-600-rgb),var(--tw-text-opacity))}.text-primary-700{--tw-text-opacity:1;color:rgba(var(--color-primary-700-rgb),var(--tw-text-opacity))}.text-primary-800{--tw-text-opacity:1;color:rgba(var(--color-primary-800-rgb),var(--tw-text-opacity))}.text-primary-900{--tw-text-opacity:1;color:rgba(var(--color-primary-900-rgb),var(--tw-text-opacity))}.text-primary-950{--tw-text-opacity:1;color:rgba(var(--color-primary-950-rgb),var(--tw-text-opacity))}.text-secondary-50{--tw-text-opacity:1;color:rgba(var(--color-secondary-50-rgb),var(--tw-text-opacity))}.text-secondary-100{--tw-text-opacity:1;color:rgba(var(--color-secondary-100-rgb),var(--tw-text-opacity))}.text-secondary-200{--tw-text-opacity:1;color:rgba(var(--color-secondary-200-rgb),var(--tw-text-opacity))}.text-secondary-300{--tw-text-opacity:1;color:rgba(var(--color-secondary-300-rgb),var(--tw-text-opacity))}.text-secondary-400{--tw-text-opacity:1;color:rgba(var(--color-secondary-400-rgb),var(--tw-text-opacity))}.text-secondary-500{--tw-text-opacity:1;color:rgba(var(--color-secondary-500-rgb),var(--tw-text-opacity))}.text-secondary-600{--tw-text-opacity:1;color:rgba(var(--color-secondary-600-rgb),var(--tw-text-opacity))}.text-secondary-700{--tw-text-opacity:1;color:rgba(var(--color-secondary-700-rgb),var(--tw-text-opacity))}.text-secondary-800{--tw-text-opacity:1;color:rgba(var(--color-secondary-800-rgb),var(--tw-text-opacity))}.text-secondary-900{--tw-text-opacity:1;color:rgba(var(--color-secondary-900-rgb),var(--tw-text-opacity))}.text-secondary-950{--tw-text-opacity:1;color:rgba(var(--color-secondary-950-rgb),var(--tw-text-opacity))}.text-gray-50{--tw-text-opacity:1;color:rgba(var(--color-gray-50-rgb),var(--tw-text-opacity))}.text-gray-100{--tw-text-opacity:1;color:rgba(var(--color-gray-100-rgb),var(--tw-text-opacity))}.text-gray-200,.text-lightest{--tw-text-opacity:1;color:rgba(var(--color-gray-200-rgb),var(--tw-text-opacity))}.text-gray-300,.text-lighter{--tw-text-opacity:1;color:rgba(var(--color-gray-300-rgb),var(--tw-text-opacity))}.text-gray-400,.text-lighten{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.text-gray,.text-gray-500{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.text-darken,.text-gray-600{--tw-text-opacity:1;color:rgba(var(--color-gray-600-rgb),var(--tw-text-opacity))}.text-darker,.text-gray-700{--tw-text-opacity:1;color:rgba(var(--color-gray-700-rgb),var(--tw-text-opacity))}.text-darkest,.text-gray-800{--tw-text-opacity:1;color:rgba(var(--color-gray-800-rgb),var(--tw-text-opacity))}.text-gray-900{--tw-text-opacity:1;color:rgba(var(--color-gray-900-rgb),var(--tw-text-opacity))}.text-gray-950{--tw-text-opacity:1;color:rgba(var(--color-gray-950-rgb),var(--tw-text-opacity))}.text-white{--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity))}.text-black{--tw-text-opacity:1;color:rgba(var(--color-black-rgb),var(--tw-text-opacity))}.text-transparent{color:transparent}.text-canvas{--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.text-surface-light{--tw-text-opacity:1;color:rgba(var(--color-surface-light-rgb),var(--tw-text-opacity))}.text-surface{--tw-text-opacity:1;color:rgba(var(--color-surface-rgb),var(--tw-text-opacity))}.text-surface-strong{--tw-text-opacity:1;color:rgba(var(--color-surface-strong-rgb),var(--tw-text-opacity))}.text-inverse{--tw-text-opacity:1;color:rgba(var(--color-inverse-rgb),var(--tw-text-opacity))}.text-fore-in-light{--tw-text-opacity:1;color:rgba(var(--color-fore-in-light-rgb),var(--tw-text-opacity))}.text-fore-in-dark{--tw-text-opacity:1;color:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity))}.text-fore{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}.text-focus{--tw-text-opacity:1;color:rgba(var(--color-focus-rgb),var(--tw-text-opacity))}.text-link{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity))}.text-link-hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}.text-current{color:currentColor}.text-inherit{color:inherit}.clip,.ellipsis,.text-clip,.text-ellipsis{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.clip,.text-clip{text-overflow:clip}.whitespace-normal{white-space:normal}.nowrap,.whitespace-nowrap{white-space:nowrap}.pre,.whitespace-pre{white-space:pre}.pre-line,.whitespace-pre-line{white-space:pre-line}.pre-wrap,.whitespace-pre-wrap{white-space:pre-wrap}.break-normal{overflow-wrap:normal;word-break:normal}.break-words{overflow-wrap:break-word}.break-all{word-break:break-all}.text-opacity-0{--tw-text-opacity:0}.text-opacity-5{--tw-text-opacity:.05}.text-opacity-10{--tw-text-opacity:.1}.text-opacity-20{--tw-text-opacity:.2}.text-opacity-25{--tw-text-opacity:.25}.text-opacity-30{--tw-text-opacity:.3}.text-opacity-40{--tw-text-opacity:.4}.text-opacity-50{--tw-text-opacity:.5}.text-opacity-60{--tw-text-opacity:.6}.text-opacity-70{--tw-text-opacity:.7}.text-opacity-80{--tw-text-opacity:.8}.text-opacity-90{--tw-text-opacity:.9}.text-opacity-95{--tw-text-opacity:.95}.text-opacity-100{--tw-text-opacity:1}.uppercase{text-transform:uppercase}.lowercase{text-transform:lowercase}.capitalize{text-transform:capitalize}.normal-case{text-transform:none}.list-none{list-style-type:none}.list-disc{list-style-type:disc}.list-decimal{list-style-type:decimal}.list-unstyled{list-style-type:none;padding-left:0}.underline{text-decoration-line:underline}.overline{text-decoration-line:overline}.line-through{text-decoration-line:line-through}.no-underline{text-decoration-line:none}.bg-primary{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity))}.bg-secondary{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-500-rgb),var(--tw-bg-opacity))}.bg-success{--tw-bg-opacity:1;background-color:rgba(var(--color-success-500-rgb),var(--tw-bg-opacity))}.bg-warning{--tw-bg-opacity:1;background-color:rgba(var(--color-warning-500-rgb),var(--tw-bg-opacity))}.bg-danger{--tw-bg-opacity:1;background-color:rgba(var(--color-danger-500-rgb),var(--tw-bg-opacity))}.bg-important{--tw-bg-opacity:1;background-color:rgba(var(--color-important-500-rgb),var(--tw-bg-opacity))}.bg-special{--tw-bg-opacity:1;background-color:rgba(var(--color-special-500-rgb),var(--tw-bg-opacity))}.bg-primary-50{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.bg-primary-100{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity))}.bg-primary-200{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-200-rgb),var(--tw-bg-opacity))}.bg-primary-300{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-300-rgb),var(--tw-bg-opacity))}.bg-primary-400{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-400-rgb),var(--tw-bg-opacity))}.bg-primary-500{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity))}.bg-primary-600{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-600-rgb),var(--tw-bg-opacity))}.bg-primary-700{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-700-rgb),var(--tw-bg-opacity))}.bg-primary-800{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-800-rgb),var(--tw-bg-opacity))}.bg-primary-900{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-900-rgb),var(--tw-bg-opacity))}.bg-primary-950{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-950-rgb),var(--tw-bg-opacity))}.bg-secondary-50{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-50-rgb),var(--tw-bg-opacity))}.bg-secondary-100{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-100-rgb),var(--tw-bg-opacity))}.bg-secondary-200{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-200-rgb),var(--tw-bg-opacity))}.bg-secondary-300{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-300-rgb),var(--tw-bg-opacity))}.bg-secondary-400{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-400-rgb),var(--tw-bg-opacity))}.bg-secondary-500{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-500-rgb),var(--tw-bg-opacity))}.bg-secondary-600{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-600-rgb),var(--tw-bg-opacity))}.bg-secondary-700{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-700-rgb),var(--tw-bg-opacity))}.bg-secondary-800{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-800-rgb),var(--tw-bg-opacity))}.bg-secondary-900{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-900-rgb),var(--tw-bg-opacity))}.bg-secondary-950{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-950-rgb),var(--tw-bg-opacity))}.bg-gray-50{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity))}.bg-gray-100{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity))}.bg-gray-200,.bg-lightest{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-200-rgb),var(--tw-bg-opacity))}.bg-gray-300,.bg-lighter{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-300-rgb),var(--tw-bg-opacity))}.bg-gray-400,.bg-light{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-400-rgb),var(--tw-bg-opacity))}.bg-gray,.bg-gray-500{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-500-rgb),var(--tw-bg-opacity))}.bg-darken,.bg-gray-600{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-600-rgb),var(--tw-bg-opacity))}.bg-darker,.bg-gray-700{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-700-rgb),var(--tw-bg-opacity))}.bg-darkest,.bg-gray-800{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-800-rgb),var(--tw-bg-opacity))}.bg-gray-900{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-900-rgb),var(--tw-bg-opacity))}.bg-gray-950{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-950-rgb),var(--tw-bg-opacity))}.bg-canvas{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.bg-surface-light{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity))}.bg-surface{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.bg-surface-strong{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-strong-rgb),var(--tw-bg-opacity))}.bg-inverse{--tw-bg-opacity:1;background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity))}.bg-fore-in-light{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-in-light-rgb),var(--tw-bg-opacity))}.bg-fore-in-dark{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-in-dark-rgb),var(--tw-bg-opacity))}.bg-fore{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-rgb),var(--tw-bg-opacity))}.bg-focus{--tw-bg-opacity:1;background-color:rgba(var(--color-focus-rgb),var(--tw-bg-opacity))}.bg-white{--tw-bg-opacity:1;background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity))}.bg-black{--tw-bg-opacity:1;background-color:rgba(var(--color-black-rgb),var(--tw-bg-opacity))}.bg-transparent{background-color:transparent}.bg-current{background-color:currentColor}.bg-inherit{background-color:inherit}.bg-none{background-image:none}.bg-opacity-0{--tw-bg-opacity:0}.bg-opacity-5{--tw-bg-opacity:.05}.bg-opacity-10{--tw-bg-opacity:.1}.bg-opacity-20{--tw-bg-opacity:.2}.bg-opacity-25{--tw-bg-opacity:.25}.bg-opacity-30{--tw-bg-opacity:.3}.bg-opacity-40{--tw-bg-opacity:.4}.bg-opacity-50{--tw-bg-opacity:.5}.bg-opacity-60{--tw-bg-opacity:.6}.bg-opacity-70{--tw-bg-opacity:.7}.bg-opacity-80{--tw-bg-opacity:.8}.bg-opacity-90{--tw-bg-opacity:.9}.bg-opacity-100{--tw-bg-opacity:1}.bg-auto{background-size:auto}.bg-cover{background-size:cover}.bg-contain{background-size:contain}.bg-repeat{background-repeat:repeat}.bg-no-repeat{background-repeat:no-repeat}.bg-repeat-x{background-repeat:repeat-x}.bg-repeat-y{background-repeat:repeat-y}.bg-repeat-round{background-repeat:round}.bg-repeat-space{background-repeat:space}.bg-bottom{background-position:bottom}.bg-center{background-position:50%}.bg-left{background-position:0}.bg-left-bottom{background-position:0 100%}.bg-left-top{background-position:0 0}.bg-right{background-position:100%}.bg-right-bottom{background-position:100% 100%}.bg-right-top{background-position:100% 0}.bg-top{background-position:top}.bg-fixed{background-attachment:fixed}.bg-local{background-attachment:local}.bg-scroll{background-attachment:scroll}.divider{align-self:stretch;border-color:currentColor;border-left-width:1px;border-top-width:1px;opacity:.1}.border-0{border-width:0}.border{border-width:1px}.border-2{border-width:2px}.border-4{border-width:4px}.border-t{border-top-width:1px}.border-l{border-left-width:1px}.border-r{border-right-width:1px}.border-b{border-bottom-width:1px}.border-t-0{border-top-width:0}.border-r-0{border-right-width:0}.border-b-0{border-bottom-width:0}.border-l-0{border-left-width:0}.border-t-2{border-top-width:2px}.border-l-2{border-left-width:2px}.border-r-2{border-right-width:2px}.border-b-2{border-bottom-width:2px}.border-t-4{border-top-width:4px}.border-l-4{border-left-width:4px}.border-r-4{border-right-width:4px}.border-b-4{border-bottom-width:4px}.border-light{--tw-border-opacity:1;border-color:rgba(var(--color-border-light-rgb),var(--tw-border-opacity))}.border-strong{--tw-border-opacity:1;border-color:rgba(var(--color-border-strong-rgb),var(--tw-border-opacity))}.border-primary{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity))}.border-secondary{--tw-border-opacity:1;border-color:rgba(var(--color-secondary-500-rgb),var(--tw-border-opacity))}.border-success{--tw-border-opacity:1;border-color:rgba(var(--color-success-500-rgb),var(--tw-border-opacity))}.border-warning{--tw-border-opacity:1;border-color:rgba(var(--color-warning-500-rgb),var(--tw-border-opacity))}.border-danger{--tw-border-opacity:1;border-color:rgba(var(--color-danger-500-rgb),var(--tw-border-opacity))}.border-important{--tw-border-opacity:1;border-color:rgba(var(--color-important-500-rgb),var(--tw-border-opacity))}.border-special{--tw-border-opacity:1;border-color:rgba(var(--color-special-500-rgb),var(--tw-border-opacity))}.border-gray-50{--tw-border-opacity:1;border-color:rgba(var(--color-gray-50-rgb),var(--tw-border-opacity))}.border-gray-100{--tw-border-opacity:1;border-color:rgba(var(--color-gray-100-rgb),var(--tw-border-opacity))}.border-gray-200{--tw-border-opacity:1;border-color:rgba(var(--color-gray-200-rgb),var(--tw-border-opacity))}.border-gray-300{--tw-border-opacity:1;border-color:rgba(var(--color-gray-300-rgb),var(--tw-border-opacity))}.border-gray-400{--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.border-gray,.border-gray-500{--tw-border-opacity:1;border-color:rgba(var(--color-gray-500-rgb),var(--tw-border-opacity))}.border-gray-600{--tw-border-opacity:1;border-color:rgba(var(--color-gray-600-rgb),var(--tw-border-opacity))}.border-gray-700{--tw-border-opacity:1;border-color:rgba(var(--color-gray-700-rgb),var(--tw-border-opacity))}.border-gray-800{--tw-border-opacity:1;border-color:rgba(var(--color-gray-800-rgb),var(--tw-border-opacity))}.border-gray-900{--tw-border-opacity:1;border-color:rgba(var(--color-gray-900-rgb),var(--tw-border-opacity))}.border-gray-950{--tw-border-opacity:1;border-color:rgba(var(--color-gray-950-rgb),var(--tw-border-opacity))}.border-white{--tw-border-opacity:1;border-color:rgba(var(--color-white-rgb),var(--tw-border-opacity))}.border-black{--tw-border-opacity:1;border-color:rgba(var(--color-black-rgb),var(--tw-border-opacity))}.border-canvas{--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity))}.border-surface-light{--tw-border-opacity:1;border-color:rgba(var(--color-surface-light-rgb),var(--tw-border-opacity))}.border-surface{--tw-border-opacity:1;border-color:rgba(var(--color-surface-rgb),var(--tw-border-opacity))}.border-surface-strong{--tw-border-opacity:1;border-color:rgba(var(--color-surface-strong-rgb),var(--tw-border-opacity))}.border-inverse{--tw-border-opacity:1;border-color:rgba(var(--color-inverse-rgb),var(--tw-border-opacity))}.border-fore-in-light{--tw-border-opacity:1;border-color:rgba(var(--color-fore-in-light-rgb),var(--tw-border-opacity))}.border-fore-in-dark{--tw-border-opacity:1;border-color:rgba(var(--color-fore-in-dark-rgb),var(--tw-border-opacity))}.border-fore{--tw-border-opacity:1;border-color:rgba(var(--color-fore-rgb),var(--tw-border-opacity))}.border-focus{--tw-border-opacity:1;border-color:rgba(var(--color-focus-rgb),var(--tw-border-opacity))}.border-link{--tw-border-opacity:1;border-color:rgba(var(--color-link-rgb),var(--tw-border-opacity))}.border-link-hover{--tw-border-opacity:1;border-color:rgba(var(--color-link-hover-rgb),var(--tw-border-opacity))}.border-transparent{border-color:transparent}.border-current{border-color:currentColor}.border-inherit{border-color:inherit}.border-solid{border-style:solid}.border-dashed{border-style:dashed}.border-dotted{border-style:dotted}.border-double{border-style:double}.border-hidden{border-style:hidden}.border-none{border-style:none}.border-opacity-0{--tw-border-opacity:0}.border-opacity-5{--tw-border-opacity:.05}.border-opacity-10{--tw-border-opacity:.1}.border-opacity-20{--tw-border-opacity:.2}.border-opacity-25{--tw-border-opacity:.25}.border-opacity-30{--tw-border-opacity:.3}.border-opacity-40{--tw-border-opacity:.4}.border-opacity-50{--tw-border-opacity:.5}.border-opacity-60{--tw-border-opacity:.6}.border-opacity-70{--tw-border-opacity:.7}.border-opacity-80{--tw-border-opacity:.8}.border-opacity-90{--tw-border-opacity:.9}.border-opacity-95{--tw-border-opacity:.95}.border-opacity-100{--tw-border-opacity:1}.rounded-none{border-radius:var(--radius-none)}.rounded-sm{border-radius:var(--radius-sm)}.rounded{border-radius:var(--radius)}.rounded-md{border-radius:var(--radius-md)}.rounded-lg{border-radius:var(--radius-lg)}.rounded-xl{border-radius:var(--radius-xl)}.rounded-2xl{border-radius:var(--radius-2xl)}.rounded-3xl{border-radius:var(--radius-3xl)}.circle,.rounded-full{border-radius:var(--radius-full)}.rounded-l-none{border-bottom-left-radius:var(--radius-none);border-top-left-radius:var(--radius-none)}.rounded-t-none{border-top-left-radius:var(--radius-none)}.rounded-r-none,.rounded-t-none{border-top-right-radius:var(--radius-none)}.rounded-b-none,.rounded-r-none{border-bottom-right-radius:var(--radius-none)}.rounded-b-none{border-bottom-left-radius:var(--radius-none)}.rounded-br-none{border-bottom-right-radius:var(--radius-none)}.rounded-bl-none{border-bottom-left-radius:var(--radius-none)}.rounded-tr-none{border-top-right-radius:var(--radius-none)}.rounded-tl-none{border-top-left-radius:var(--radius-none)}.ring{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.ring-border-light{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-light-rgb),var(--tw-ring-opacity))}.ring-border{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.ring-border-strong{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.ring-light{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05}.ring-gray{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.1}.ring-dark{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.2}.ring-darker{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.3}.ring-darkest{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.5}.ring-primary{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-500-rgb),var(--tw-ring-opacity))}.ring-secondary{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-secondary-500-rgb),var(--tw-ring-opacity))}.ring-warning{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-warning-500-rgb),var(--tw-ring-opacity))}.ring-success{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-success-500-rgb),var(--tw-ring-opacity))}.ring-danger{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-danger-500-rgb),var(--tw-ring-opacity))}.ring-important{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-important-500-rgb),var(--tw-ring-opacity))}.ring-special{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-special-500-rgb),var(--tw-ring-opacity))}.ring-gray-50{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-50-rgb),var(--tw-ring-opacity))}.ring-gray-100{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-100-rgb),var(--tw-ring-opacity))}.ring-gray-200{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-200-rgb),var(--tw-ring-opacity))}.ring-gray-300{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-300-rgb),var(--tw-ring-opacity))}.ring-gray-400{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-400-rgb),var(--tw-ring-opacity))}.ring-gray-500{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-500-rgb),var(--tw-ring-opacity))}.ring-gray-600{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-600-rgb),var(--tw-ring-opacity))}.ring-gray-700{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-700-rgb),var(--tw-ring-opacity))}.ring-gray-800{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-800-rgb),var(--tw-ring-opacity))}.ring-gray-900{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-900-rgb),var(--tw-ring-opacity))}.ring-gray-950{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-950-rgb),var(--tw-ring-opacity))}.ring-inverse{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity))}.ring-canvas{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-canvas-rgb),var(--tw-ring-opacity))}.ring-surface{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-rgb),var(--tw-ring-opacity))}.ring-fore{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-fore-rgb),var(--tw-ring-opacity))}.ring-transparent{--tw-ring-color:transparent}.ring-black{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-black-rgb),var(--tw-ring-opacity))}.ring-white{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-white-rgb),var(--tw-ring-opacity))}.ring-inherit{--tw-ring-color:inherit}.ring-current{--tw-ring-color:currentColor}.ring-opacity-0{--tw-ring-opacity:0}.ring-opacity-5{--tw-ring-opacity:.05}.ring-opacity-10{--tw-ring-opacity:.1}.ring-opacity-20{--tw-ring-opacity:.2}.ring-opacity-30{--tw-ring-opacity:.3}.ring-opacity-40{--tw-ring-opacity:.4}.ring-opacity-50{--tw-ring-opacity:.5}.ring-opacity-60{--tw-ring-opacity:.6}.ring-opacity-70{--tw-ring-opacity:.7}.ring-opacity-80{--tw-ring-opacity:.8}.ring-opacity-90{--tw-ring-opacity:.9}.ring-opacity-100{--tw-ring-opacity:1}.ring-0{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-0,.ring-2{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-2{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-3{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-3,.ring-4{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-4{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(4px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-8{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(8px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-inset{--tw-ring-inset:inset}.ring-offset-0{--tw-ring-offset-width:0px}.ring-offset-1{--tw-ring-offset-width:1px}.ring-offset-2{--tw-ring-offset-width:2px}.ring-offset-4{--tw-ring-offset-width:4px}.ring-offset-8{--tw-ring-offset-width:8px}.shadow-sm{--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color)}.shadow,.shadow-sm{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color)}.shadow-md{--tw-shadow:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--tw-shadow-colored:0 2px 6px -1px var(--tw-shadow-color),0 1px 4px -2px var(--tw-shadow-color)}.shadow-lg,.shadow-md{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-lg{--tw-shadow:0 5px 15px -3px rgba(0,0,0,.2),0 2px 6px -4px rgba(0,0,0,.15);--tw-shadow-colored:0 5px 15px -3px var(--tw-shadow-color),0 2px 6px -4px var(--tw-shadow-color)}.shadow-xl{--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color)}.shadow-2xl,.shadow-xl{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-2xl{--tw-shadow:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--tw-shadow-colored:0 10px 50px -10px var(--tw-shadow-color),0 8px 20px -10px var(--tw-shadow-color)}.shadow-inner{--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color)}.shadow-inner,.shadow-none{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-none{--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000}.muted{opacity:var(--opacity-muted)}.opacity-0{opacity:0}.opacity-5{opacity:.05}.opacity-10{opacity:.1}.opacity-20{opacity:.2}.opacity-25{opacity:.25}.opacity-30{opacity:.3}.opacity-40{opacity:.4}.opacity-50{opacity:.5}.opacity-60{opacity:.6}.opacity-70{opacity:.7}.opacity-75{opacity:.75}.opacity-80{opacity:.8}.opacity-90{opacity:.9}.opacity-95{opacity:.95}.opacity-100{opacity:1}.blur-none{--tw-blur:blur(0)}.blur-none,.blur-sm{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-sm{--tw-blur:blur(4px)}.blur{--tw-blur:blur(8px)}.blur,.blur-md{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-md{--tw-blur:blur(12px)}.blur-lg{--tw-blur:blur(16px)}.blur-lg,.blur-xl{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-xl{--tw-blur:blur(24px)}.grayscale{--tw-grayscale:grayscale(100%)}.grayscale,.invert{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.invert{--tw-invert:invert(100%)}.filter-none{filter:none!important}.drop-shadow-none{--tw-drop-shadow:drop-shadow(0 0 #0000)}.drop-shadow-none,.drop-shadow-sm{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-sm{--tw-drop-shadow:drop-shadow(0 1px 1px rgba(0,0,0,.05))}.drop-shadow{--tw-drop-shadow:drop-shadow(0 1px 2px rgba(0,0,0,.1)) drop-shadow(0 1px 1px rgba(0,0,0,.06))}.drop-shadow,.drop-shadow-md{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-md{--tw-drop-shadow:drop-shadow(0 4px 3px rgba(0,0,0,.07)) drop-shadow(0 2px 2px rgba(0,0,0,.06))}.drop-shadow-lg{--tw-drop-shadow:drop-shadow(0 10px 8px rgba(0,0,0,.04)) drop-shadow(0 4px 3px rgba(0,0,0,.1))}.drop-shadow-lg,.drop-shadow-xl{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-xl{--tw-drop-shadow:drop-shadow(0 20px 13px rgba(0,0,0,.03)) drop-shadow(0 8px 5px rgba(0,0,0,.08))}.drop-shadow-2xl{--tw-drop-shadow:drop-shadow(0 25px 25px rgba(0,0,0,.15));filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.backdrop-blur-none{--tw-backdrop-blur:blur(0)}.backdrop-blur-none,.backdrop-blur-sm{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-sm{--tw-backdrop-blur:blur(4px)}.backdrop-blur{--tw-backdrop-blur:blur(8px)}.backdrop-blur,.backdrop-blur-md{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-md{--tw-backdrop-blur:blur(12px)}.backdrop-blur-lg{--tw-backdrop-blur:blur(16px)}.backdrop-blur-lg,.backdrop-blur-xl{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-xl{--tw-backdrop-blur:blur(24px)}.backdrop-blur-2xl{--tw-backdrop-blur:blur(40px)}.backdrop-blur-2xl,.backdrop-blur-3xl{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-3xl{--tw-backdrop-blur:blur(64px)}.transition{transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter,-webkit-backdrop-filter;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-all{transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-colors{transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-opacity{transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-shadow{transition-duration:.15s;transition-property:box-shadow;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-transform{transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-none{transition-property:none}.fade,.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{opacity:0;transition-duration:.15s;transition-property:opacity,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{--tw-scale-x:.9;--tw-scale-y:.9}.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-bottom{--tw-translate-y:25%}.fade-from-top{--tw-translate-y:-25%}.fade-from-left,.fade-from-top{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-left{--tw-translate-x:-25%}.fade-from-right{--tw-translate-x:25%}.fade-from-bottom.in,.fade-from-center.in,.fade-from-left.in,.fade-from-right,.fade-from-right.in,.fade-from-top.in,.fade.in{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-bottom.in,.fade-from-center.in,.fade-from-left.in,.fade-from-right.in,.fade-from-top.in,.fade.in{--tw-translate-x:0px;--tw-translate-y:0px;--tw-scale-x:1;--tw-scale-y:1;opacity:1}.duration-75{transition-duration:75ms}.duration-100{transition-duration:.1s}.duration-200{transition-duration:.2s}.duration-300{transition-duration:.3s}.duration-500{transition-duration:.5s}.duration-1000{transition-duration:1s}@keyframes -spin{to{transform:rotate(1turn)}}.animate-spin,.spin{animation:-spin 1s linear infinite}@keyframes -ping{75%,to{opacity:0;transform:scale(2)}}.animate-ping,.ping{animation:-ping 1s cubic-bezier(0,0,.2,1) infinite}@keyframes -pulse{50%{opacity:.5}}.animate-pulse,.pulse{animation:-pulse 2s cubic-bezier(.4,0,.6,1) infinite}@keyframes -bounce{0%,to{animation-timing-function:cubic-bezier(.8,0,1,1);transform:translateY(-25%)}50%{animation-timing-function:cubic-bezier(0,0,.2,1);transform:none}}.animate-bounce,.bounce{animation:-bounce 1s infinite}.scale-0{--tw-scale-x:0;--tw-scale-y:0}.scale-0,.scale-50{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-50{--tw-scale-x:.5;--tw-scale-y:.5}.scale-75{--tw-scale-x:.75;--tw-scale-y:.75}.scale-75,.scale-90{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-90{--tw-scale-x:.9;--tw-scale-y:.9}.scale-95{--tw-scale-x:.95;--tw-scale-y:.95}.scale-100,.scale-95{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-100{--tw-scale-x:1;--tw-scale-y:1}.scale-105{--tw-scale-x:1.05;--tw-scale-y:1.05}.scale-105,.scale-110{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-110{--tw-scale-x:1.1;--tw-scale-y:1.1}.scale-125{--tw-scale-x:1.25;--tw-scale-y:1.25}.scale-125,.scale-150{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-150{--tw-scale-x:1.5;--tw-scale-y:1.5}.flip-x{--tw-scale-x:-1}.flip-x,.flip-y{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.flip-y{--tw-scale-y:-1}.rotate-0{--tw-rotate:0deg}.rotate-0,.rotate-1{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-1{--tw-rotate:1deg}.rotate-2{--tw-rotate:2deg}.rotate-2,.rotate-3{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-3{--tw-rotate:3deg}.rotate-6{--tw-rotate:6deg}.rotate-12,.rotate-6{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-12{--tw-rotate:12deg}.rotate-45{--tw-rotate:45deg}.rotate-45,.rotate-90{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-90{--tw-rotate:90deg}.rotate-135{--tw-rotate:135deg}.rotate-135,.rotate-180{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-180{--tw-rotate:180deg}.rotate-270{--tw-rotate:270deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.basis-0{flex-basis:0px}.basis-1{flex-basis:0.25rem}.basis-2{flex-basis:0.5rem}.basis-3{flex-basis:0.75rem}.basis-4{flex-basis:1rem}.basis-5{flex-basis:1.25rem}.basis-6{flex-basis:1.5rem}.basis-7{flex-basis:1.75rem}.basis-8{flex-basis:2rem}.basis-9{flex-basis:2.25rem}.basis-10{flex-basis:2.5rem}.basis-11{flex-basis:2.75rem}.basis-12{flex-basis:3rem}.basis-14{flex-basis:3.5rem}.basis-16{flex-basis:4rem}.basis-20{flex-basis:5rem}.basis-24{flex-basis:6rem}.basis-28{flex-basis:7rem}.basis-32{flex-basis:8rem}.basis-36{flex-basis:9rem}.basis-40{flex-basis:10rem}.basis-44{flex-basis:11rem}.basis-48{flex-basis:12rem}.basis-52{flex-basis:13rem}.basis-56{flex-basis:14rem}.basis-60{flex-basis:15rem}.basis-64{flex-basis:16rem}.basis-72{flex-basis:18rem}.basis-80{flex-basis:20rem}.basis-96{flex-basis:24rem}.basis-auto{flex-basis:auto}.basis-px{flex-basis:1px}.basis-0\.5{flex-basis:0.125rem}.basis-1\.5{flex-basis:0.375rem}.basis-2\.5{flex-basis:0.625rem}.basis-3\.5{flex-basis:0.875rem}.basis-1\/2{flex-basis:50%}.basis-1\/3{flex-basis:33.333333%}.basis-2\/3{flex-basis:66.666667%}.basis-1\/4{flex-basis:25%}.basis-2\/4{flex-basis:50%}.basis-3\/4{flex-basis:75%}.basis-1\/5{flex-basis:20%}.basis-2\/5{flex-basis:40%}.basis-3\/5{flex-basis:60%}.basis-4\/5{flex-basis:80%}.basis-1\/6{flex-basis:16.666667%}.basis-2\/6{flex-basis:33.333333%}.basis-3\/6{flex-basis:50%}.basis-4\/6{flex-basis:66.666667%}.basis-5\/6{flex-basis:83.333333%}.basis-1\/12{flex-basis:8.333333%}.basis-2\/12{flex-basis:16.666667%}.basis-3\/12{flex-basis:25%}.basis-4\/12{flex-basis:33.333333%}.basis-5\/12{flex-basis:41.666667%}.basis-6\/12{flex-basis:50%}.basis-7\/12{flex-basis:58.333333%}.basis-8\/12{flex-basis:66.666667%}.basis-9\/12{flex-basis:75%}.basis-10\/12{flex-basis:83.333333%}.basis-11\/12{flex-basis:91.666667%}.basis-full{flex-basis:100%}.row{display:flex;flex-direction:row}.center,.col{display:flex;flex-direction:column}.center,.center-row{align-items:center;justify-content:center}.center-row{display:flex;flex-direction:row}.center-x,.center-y{align-items:center;display:flex}.center-y{flex-direction:column}.row-reverse{display:flex;flex-direction:row-reverse}.col-reverse{display:flex;flex-direction:column-reverse}.flex-wrap{flex-wrap:wrap}.flex-wrap-reverse{flex-wrap:wrap-reverse}.flex-nowrap{flex-wrap:nowrap}.flex-1{flex:1 1 0%}.flex-auto{flex:1 1 auto}.flex-initial{flex:0 1 auto}.flex-none{flex:none}.grow{flex-grow:1!important}.grow-0{flex-grow:0!important}.shrink{flex-shrink:1}.shrink-0{flex-shrink:0}.order-1{order:1}.order-2{order:2}.order-3{order:3}.order-4{order:4}.order-5{order:5}.order-6{order:6}.order-7{order:7}.order-8{order:8}.order-9{order:9}.order-10{order:10}.order-11{order:11}.order-12{order:12}.order-first{order:-9999}.order-last{order:9999}.order-none{order:0}.gap-0{gap:0}.gap-x-0{-moz-column-gap:0;column-gap:0}.gap-y-0{row-gap:0}.gap-px{gap:1px}.gap-x-px{-moz-column-gap:1px;column-gap:1px}.gap-y-px{row-gap:1px}.gap-0\.5{gap:.125rem}.gap-x-0\.5{-moz-column-gap:.125rem;column-gap:.125rem}.gap-y-0\.5{row-gap:.125rem}.gap-3px{gap:3px}.gap-1{gap:.25rem}.gap-x-1{-moz-column-gap:.25rem;column-gap:.25rem}.gap-y-1{row-gap:.25rem}.gap-1\.5{gap:.375rem}.gap-x-1\.5{-moz-column-gap:.375rem;column-gap:.375rem}.gap-y-1\.5{row-gap:.375rem}.gap-2{gap:.5rem}.gap-x-2{-moz-column-gap:.5rem;column-gap:.5rem}.gap-y-2{row-gap:.5rem}.gap-2\.5{gap:.625rem}.gap-x-2\.5{-moz-column-gap:.625rem;column-gap:.625rem}.gap-y-2\.5{row-gap:.625rem}.gap-3{gap:.75rem}.gap-x-3{-moz-column-gap:.75rem;column-gap:.75rem}.gap-y-3{row-gap:.75rem}.gap-3\.5{gap:.875rem}.gap-x-3\.5{-moz-column-gap:.875rem;column-gap:.875rem}.gap-y-3\.5{row-gap:.875rem}.gap-4{gap:1rem}.gap-x-4{-moz-column-gap:1rem;column-gap:1rem}.gap-y-4{row-gap:1rem}.gap-5{gap:1.25rem}.gap-x-5{-moz-column-gap:1.25rem;column-gap:1.25rem}.gap-y-5{row-gap:1.25rem}.gap-6{gap:1.5rem}.gap-x-6{-moz-column-gap:1.5rem;column-gap:1.5rem}.gap-y-6{row-gap:1.5rem}.gap-7{gap:1.75rem}.gap-x-7{-moz-column-gap:1.75rem;column-gap:1.75rem}.gap-y-7{row-gap:1.75rem}.gap-8{gap:2rem}.gap-x-8{-moz-column-gap:2rem;column-gap:2rem}.gap-y-8{row-gap:2rem}.justify-start{justify-content:flex-start}.justify-end{justify-content:flex-end}.justify-center{justify-content:center}.justify-between{justify-content:space-between}.justify-around{justify-content:space-around}.justify-evenly{justify-content:space-evenly}.self-auto{align-self:auto}.self-start{align-self:flex-start}.self-end{align-self:flex-end}.self-center{align-self:center}.self-stretch{align-self:stretch}.self-baseline{align-self:baseline}.content-center{align-content:center}.content-start{align-content:flex-start}.content-end{align-content:flex-end}.content-between{align-content:space-between}.content-around{align-content:space-around}.content-evenly{align-content:space-evenly}.items-start{align-items:flex-start}.items-end{align-items:flex-end}.items-center{align-items:center}.items-baseline{align-items:baseline}.items-stretch{align-items:stretch}@font-face{font-display:fallback;font-family:D-DIN-PRO;font-weight:400;src:url(./fonts/D-DIN-PRO-400-Regular.otf)}@font-face{font-display:fallback;font-family:D-DIN-PRO;font-weight:500;src:url(./fonts/D-DIN-PRO-700-Bold.otf)}.num{font-family:D-DIN-PRO}@font-face{font-display:fallback;font-family:Nunito;font-weight:400;src:url(./fonts/Nunito-Regular.ttf)}@font-face{font-display:fallback;font-family:Nunito;font-weight:700;src:url(./fonts/Nunito-Bold.ttf)}@font-face{font-display:fallback;font-family:Nunito;font-weight:300;src:url(./fonts/Nunito-Light.ttf)}.font-brand{font-family:Nunito;font-weight:400}@supports not (gap:4px){.gap-px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1px*(1 - var(--tw-space-x-reverse)));margin-right:calc(1px*var(--tw-space-x-reverse))}.gap-0\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2px*(1 - var(--tw-space-x-reverse)));margin-right:calc(2px*var(--tw-space-x-reverse))}.gap-3px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(3px*(1 - var(--tw-space-x-reverse)));margin-right:calc(3px*var(--tw-space-x-reverse))}.gap-1>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}.gap-1\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(6px*(1 - var(--tw-space-x-reverse)));margin-right:calc(6px*var(--tw-space-x-reverse))}.gap-2>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.5rem*var(--tw-space-x-reverse))}.gap-2\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(10px*(1 - var(--tw-space-x-reverse)));margin-right:calc(10px*var(--tw-space-x-reverse))}.gap-3>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.75rem*var(--tw-space-x-reverse))}.gap-3\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(14px*(1 - var(--tw-space-x-reverse)));margin-right:calc(14px*var(--tw-space-x-reverse))}.gap-4>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1rem*var(--tw-space-x-reverse))}.gap-5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.25rem*var(--tw-space-x-reverse))}.gap-6>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.5rem*var(--tw-space-x-reverse))}.gap-7>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.75rem*var(--tw-space-x-reverse))}.gap-8>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2rem*var(--tw-space-x-reverse))}.col.gap-px>:not([hidden])~:not([hidden]),.gap-px.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1px*var(--tw-space-y-reverse));margin-top:calc(1px*(1 - var(--tw-space-y-reverse)))}.col.gap-0\.5>:not([hidden])~:not([hidden]),.gap-0\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2px*var(--tw-space-y-reverse));margin-top:calc(2px*(1 - var(--tw-space-y-reverse)))}.col.gap-3px>:not([hidden])~:not([hidden]),.gap-3px.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(3px*var(--tw-space-y-reverse));margin-top:calc(3px*(1 - var(--tw-space-y-reverse)))}.col.gap-1>:not([hidden])~:not([hidden]),.gap-1.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.25rem*var(--tw-space-y-reverse));margin-top:calc(.25rem*(1 - var(--tw-space-y-reverse)))}.col.gap-1\.5>:not([hidden])~:not([hidden]),.gap-1\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(6px*var(--tw-space-y-reverse));margin-top:calc(6px*(1 - var(--tw-space-y-reverse)))}.col.gap-2>:not([hidden])~:not([hidden]),.gap-2.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.col.gap-2\.5>:not([hidden])~:not([hidden]),.gap-2\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(10px*var(--tw-space-y-reverse));margin-top:calc(10px*(1 - var(--tw-space-y-reverse)))}.col.gap-3>:not([hidden])~:not([hidden]),.gap-3.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.75rem*var(--tw-space-y-reverse));margin-top:calc(.75rem*(1 - var(--tw-space-y-reverse)))}.col.gap-3\.5>:not([hidden])~:not([hidden]),.gap-3\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(14px*var(--tw-space-y-reverse));margin-top:calc(14px*(1 - var(--tw-space-y-reverse)))}.col.gap-4>:not([hidden])~:not([hidden]),.gap-4.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.col.gap-5>:not([hidden])~:not([hidden]),.gap-5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.25rem*var(--tw-space-y-reverse));margin-top:calc(1.25rem*(1 - var(--tw-space-y-reverse)))}.col.gap-6>:not([hidden])~:not([hidden]),.gap-6.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.5rem*var(--tw-space-y-reverse));margin-top:calc(1.5rem*(1 - var(--tw-space-y-reverse)))}.col.gap-7>:not([hidden])~:not([hidden]),.gap-7.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.75rem*var(--tw-space-y-reverse));margin-top:calc(1.75rem*(1 - var(--tw-space-y-reverse)))}.col.gap-8>:not([hidden])~:not([hidden]),.gap-8.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2rem*var(--tw-space-y-reverse));margin-top:calc(2rem*(1 - var(--tw-space-y-reverse)))}.nav-item>a>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}}
\ No newline at end of file
+/*! tailwindcss v3.4.4 | MIT License | https://tailwindcss.com*/*,:after,:before{border-color:rgb(var(--color-gray-200-rgb));border-style:solid;border-width:0;box-sizing:border-box}:after,:before{--tw-content:""}:host,html{line-height:1.5;-webkit-text-size-adjust:100%;font-family:-apple-system,Noto Sans,Helvetica Neue,Helvetica,Nimbus Sans L,Arial,Liberation Sans,PingFang SC,Hiragino Sans GB,Noto Sans CJK SC,Source Han Sans SC,Source Han Sans CN,Microsoft YaHei,Wenquanyi Micro Hei,WenQuanYi Zen Hei,ST Heiti,SimHei,WenQuanYi Zen Hei Sharp,sans-serif;font-feature-settings:normal;font-variation-settings:normal;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-tap-highlight-color:transparent}body{line-height:inherit;margin:0}hr{border-top-width:1px;color:inherit;height:0}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,pre,samp{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace;font-feature-settings:normal;font-size:1em;font-variation-settings:normal}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}table{border-collapse:collapse;border-color:inherit;text-indent:0}button,input,optgroup,select,textarea{color:inherit;font-family:inherit;font-feature-settings:inherit;font-size:100%;font-variation-settings:inherit;font-weight:inherit;letter-spacing:inherit;line-height:inherit;margin:0;padding:0}button,select{text-transform:none}button,input:where([type=button]),input:where([type=reset]),input:where([type=submit]){-webkit-appearance:button;background-color:transparent;background-image:none}:-moz-focusring{outline:auto}:-moz-ui-invalid{box-shadow:none}progress{vertical-align:baseline}::-webkit-inner-spin-button,::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}summary{display:list-item}blockquote,dd,dl,figure,h1,h2,h3,h4,h5,h6,hr,p,pre{margin:0}fieldset{margin:0}fieldset,legend{padding:0}menu,ol,ul{list-style:none;margin:0;padding:0}dialog{padding:0}textarea{resize:vertical}input::-moz-placeholder,textarea::-moz-placeholder{color:rgb(var(--color-gray-400-rgb));opacity:1}input::placeholder,textarea::placeholder{color:rgb(var(--color-gray-400-rgb));opacity:1}[role=button],button{cursor:pointer}:disabled{cursor:default}audio,canvas,embed,iframe,img,object,svg,video{display:block;vertical-align:middle}img,video{height:auto;max-width:100%}[hidden]{display:none}:root{--screen-2xl:1720px;--color-gray-50:#fcfdfe;--color-gray-100:#eff1f3;--color-gray-200:#ebedf3;--color-gray-300:#d2d6e5;--color-gray-400:#b2b9c5;--color-gray-500:#64758b;--color-gray-600:#4a577f;--color-gray-700:#3d4667;--color-gray-800:#353d57;--color-gray-900:#30394a;--color-gray-950:#0b0f18;--color-gray-50-rgb:252,253,254;--color-gray-100-rgb:239,241,243;--color-gray-200-rgb:235,237,243;--color-gray-300-rgb:210,214,229;--color-gray-400-rgb:178,185,197;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:74,87,127;--color-gray-700-rgb:61,70,103;--color-gray-800-rgb:53,61,87;--color-gray-900-rgb:48,57,74;--color-gray-950-rgb:11,15,24;--color-primary-50:#eef6ff;--color-primary-100:#d9eaff;--color-primary-200:#bcdcff;--color-primary-300:#8ec6ff;--color-primary-400:#59a5ff;--color-primary-500:#3883fa;--color-primary-600:#2b67e5;--color-primary-700:#144ce1;--color-primary-800:#173db6;--color-primary-900:#19388f;--color-primary-950:#142457;--color-primary-50-rgb:238,246,255;--color-primary-100-rgb:217,234,255;--color-primary-200-rgb:188,220,255;--color-primary-300-rgb:142,198,255;--color-primary-400-rgb:89,165,255;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:43,103,229;--color-primary-700-rgb:20,76,225;--color-primary-800-rgb:23,61,182;--color-primary-900-rgb:25,56,143;--color-primary-950-rgb:20,36,87;--color-secondary-50:#e7f6ff;--color-secondary-100:#cdecff;--color-secondary-200:#9bd9ff;--color-secondary-300:#77cbff;--color-secondary-400:#60c2ff;--color-secondary-500:#37b2fe;--color-secondary-600:#18a6fd;--color-secondary-700:#1099ed;--color-secondary-800:#078ada;--color-secondary-900:#046bab;--color-secondary-950:#062a4b;--color-secondary-50-rgb:231,246,255;--color-secondary-100-rgb:205,236,255;--color-secondary-200-rgb:155,217,255;--color-secondary-300-rgb:119,203,255;--color-secondary-400-rgb:96,194,255;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:24,166,253;--color-secondary-700-rgb:16,153,237;--color-secondary-800-rgb:7,138,218;--color-secondary-900-rgb:4,107,171;--color-secondary-950-rgb:6,42,75;--color-success-50:#effaf6;--color-success-100:#d6f2e7;--color-success-200:#ade5ce;--color-success-300:#83d7b6;--color-success-400:#5aca9d;--color-success-500:#31bd85;--color-success-600:#2ba675;--color-success-700:#28996c;--color-success-800:#21805a;--color-success-900:#185e3b;--color-success-950:#0e3421;--color-success-50-rgb:239,250,246;--color-success-100-rgb:214,242,231;--color-success-200-rgb:173,229,206;--color-success-300-rgb:131,215,182;--color-success-400-rgb:90,202,157;--color-success-500-rgb:49,189,133;--color-success-600-rgb:43,166,117;--color-success-700-rgb:40,153,108;--color-success-800-rgb:33,128,90;--color-success-900-rgb:24,94,59;--color-success-950-rgb:14,52,33;--color-warning-50:#fff4ea;--color-warning-100:#ffecdb;--color-warning-200:#ffd2a9;--color-warning-300:#ffbc7e;--color-warning-400:#ffaf65;--color-warning-500:#ff9f46;--color-warning-600:#f38f19;--color-warning-700:#ed8307;--color-warning-800:#d17100;--color-warning-900:#af5f01;--color-warning-950:#441506;--color-warning-50-rgb:255,244,234;--color-warning-100-rgb:255,236,219;--color-warning-200-rgb:255,210,169;--color-warning-300-rgb:255,188,126;--color-warning-400-rgb:255,175,101;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:243,143,25;--color-warning-700-rgb:237,131,7;--color-warning-800-rgb:209,113,0;--color-warning-900-rgb:175,95,1;--color-warning-950-rgb:68,21,6;--color-danger-50:#ffebeb;--color-danger-100:#ffd5d5;--color-danger-200:#ffb1b1;--color-danger-300:#ff9292;--color-danger-400:#ff7c7c;--color-danger-500:#fc5959;--color-danger-600:#fb2b2b;--color-danger-700:#d91b1b;--color-danger-800:#ba1313;--color-danger-900:#a20606;--color-danger-950:#470808;--color-danger-50-rgb:255,235,235;--color-danger-100-rgb:255,213,213;--color-danger-200-rgb:255,177,177;--color-danger-300-rgb:255,146,146;--color-danger-400-rgb:255,124,124;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:251,43,43;--color-danger-700-rgb:217,27,27;--color-danger-800-rgb:186,19,19;--color-danger-900-rgb:162,6,6;--color-danger-950-rgb:71,8,8;--color-important-50:#fff8f5;--color-important-100:#ffe2d9;--color-important-200:#ffcebf;--color-important-300:#ffb29b;--color-important-400:#ff8c68;--color-important-500:#ff8058;--color-important-600:#ff6f42;--color-important-700:#ff4912;--color-important-800:#c83509;--color-important-900:#611700;--color-important-950:#440609;--color-important-50-rgb:255,248,245;--color-important-100-rgb:255,226,217;--color-important-200-rgb:255,206,191;--color-important-300-rgb:255,178,155;--color-important-400-rgb:255,140,104;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,111,66;--color-important-700-rgb:255,73,18;--color-important-800-rgb:200,53,9;--color-important-900-rgb:97,23,0;--color-important-950-rgb:68,6,9;--color-special-50:#efecfa;--color-special-100:#e4dff7;--color-special-200:#c4b6ff;--color-special-300:#a38cff;--color-special-400:#8a6ff5;--color-special-500:#8166ee;--color-special-600:#7055df;--color-special-700:#513baa;--color-special-800:#452da5;--color-special-900:#30216e;--color-special-950:#271560;--color-special-50-rgb:239,236,250;--color-special-100-rgb:228,223,247;--color-special-200-rgb:196,182,255;--color-special-300-rgb:163,140,255;--color-special-400-rgb:138,111,245;--color-special-500-rgb:129,102,238;--color-special-600-rgb:112,85,223;--color-special-700-rgb:81,59,170;--color-special-800-rgb:69,45,165;--color-special-900-rgb:48,33,110;--color-special-950-rgb:39,21,96;--color-inherit:inherit;--color-transparent:transparent;--color-current:currentColor;--color-black:#000;--color-white:#fff;--color-canvas:#fff;--color-canvas-light:#fff;--color-canvas-dark:#fcfdfe;--color-inverse:#000;--color-surface:#eff1f3;--color-surface-light:#fcfdfe;--color-surface-strong:#ebedf3;--color-fore:#30394a;--color-fore-in-light:#30394a;--color-fore-in-dark:#fff;--color-focus:#bcdcff;--color-link:#2b47a2;--color-link-hover:#144ce1;--color-link-visited:#6328a4;--color-link-active:#144ce1;--color-placeholder:#64758b;--color-border:#ebedf3;--color-border-strong:#d2d6e5;--color-border-light:#eff1f3;--color-black-rgb:0,0,0;--color-white-rgb:255,255,255;--color-canvas-rgb:255,255,255;--color-canvas-light-rgb:255,255,255;--color-canvas-dark-rgb:252,253,254;--color-inverse-rgb:0,0,0;--color-surface-rgb:239,241,243;--color-surface-light-rgb:252,253,254;--color-surface-strong-rgb:235,237,243;--color-fore-rgb:48,57,74;--color-fore-in-light-rgb:48,57,74;--color-fore-in-dark-rgb:255,255,255;--color-focus-rgb:188,220,255;--color-link-rgb:43,71,162;--color-link-hover-rgb:20,76,225;--color-link-visited-rgb:99,40,164;--color-link-active-rgb:20,76,225;--color-placeholder-rgb:100,117,139;--color-border-rgb:235,237,243;--color-border-strong-rgb:210,214,229;--color-border-light-rgb:239,241,243;--radius-none:0px;--radius-sm:0.0625rem;--radius:0.125rem;--radius-md:0.25rem;--radius-lg:0.375rem;--radius-xl:0.5rem;--radius-2xl:0.75rem;--radius-3xl:1rem;--radius-full:9999px;--shadow-sm:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--shadow-md:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--shadow-lg:0 5px 15px -3px rgba(0,0,0,.2),0 2px 6px -4px rgba(0,0,0,.15);--shadow-xl:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--shadow-2xl:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--shadow-inner:inset 0 2px 4px 0 rgba(0,0,0,.05);--shadow-none:none;--space:0.25rem;--font-size-article:0.875rem;--font-size-root:16px;--font-size-page-lineHeight:1.5384615385}.dark{--color-gray-50:#0b0f18;--color-gray-100:#30394a;--color-gray-200:#353d57;--color-gray-300:#3d4667;--color-gray-400:#4a577f;--color-gray-500:#64758b;--color-gray-600:#b2b9c5;--color-gray-700:#d2d6e5;--color-gray-800:#ebedf3;--color-gray-900:#eff1f3;--color-gray-950:#fcfdfe;--color-gray-50-rgb:11,15,24;--color-gray-100-rgb:48,57,74;--color-gray-200-rgb:53,61,87;--color-gray-300-rgb:61,70,103;--color-gray-400-rgb:74,87,127;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:178,185,197;--color-gray-700-rgb:210,214,229;--color-gray-800-rgb:235,237,243;--color-gray-900-rgb:239,241,243;--color-gray-950-rgb:252,253,254;--color-primary-50:#142457;--color-primary-100:#19388f;--color-primary-200:#173db6;--color-primary-300:#144ce1;--color-primary-400:#2b67e5;--color-primary-500:#3883fa;--color-primary-600:#59a5ff;--color-primary-700:#8ec6ff;--color-primary-800:#bcdcff;--color-primary-900:#d9eaff;--color-primary-950:#eef6ff;--color-primary-50-rgb:20,36,87;--color-primary-100-rgb:25,56,143;--color-primary-200-rgb:23,61,182;--color-primary-300-rgb:20,76,225;--color-primary-400-rgb:43,103,229;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:89,165,255;--color-primary-700-rgb:142,198,255;--color-primary-800-rgb:188,220,255;--color-primary-900-rgb:217,234,255;--color-primary-950-rgb:238,246,255;--color-secondary-50:#062a4b;--color-secondary-100:#046bab;--color-secondary-200:#078ada;--color-secondary-300:#1099ed;--color-secondary-400:#18a6fd;--color-secondary-500:#37b2fe;--color-secondary-600:#60c2ff;--color-secondary-700:#77cbff;--color-secondary-800:#9bd9ff;--color-secondary-900:#cdecff;--color-secondary-950:#e7f6ff;--color-secondary-50-rgb:6,42,75;--color-secondary-100-rgb:4,107,171;--color-secondary-200-rgb:7,138,218;--color-secondary-300-rgb:16,153,237;--color-secondary-400-rgb:24,166,253;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:96,194,255;--color-secondary-700-rgb:119,203,255;--color-secondary-800-rgb:155,217,255;--color-secondary-900-rgb:205,236,255;--color-secondary-950-rgb:231,246,255;--color-success-50:#0e3421;--color-success-100:#185e3b;--color-success-200:#21805a;--color-success-300:#28996c;--color-success-400:#2ba675;--color-success-500:#31bd85;--color-success-600:#5aca9d;--color-success-700:#83d7b6;--color-success-800:#ade5ce;--color-success-900:#d6f2e7;--color-success-950:#effaf6;--color-success-50-rgb:14,52,33;--color-success-100-rgb:24,94,59;--color-success-200-rgb:33,128,90;--color-success-300-rgb:40,153,108;--color-success-400-rgb:43,166,117;--color-success-500-rgb:49,189,133;--color-success-600-rgb:90,202,157;--color-success-700-rgb:131,215,182;--color-success-800-rgb:173,229,206;--color-success-900-rgb:214,242,231;--color-success-950-rgb:239,250,246;--color-warning-50:#441506;--color-warning-100:#af5f01;--color-warning-200:#d17100;--color-warning-300:#ed8307;--color-warning-400:#f38f19;--color-warning-500:#ff9f46;--color-warning-600:#ffaf65;--color-warning-700:#ffbc7e;--color-warning-800:#ffd2a9;--color-warning-900:#ffecdb;--color-warning-950:#fff4ea;--color-warning-50-rgb:68,21,6;--color-warning-100-rgb:175,95,1;--color-warning-200-rgb:209,113,0;--color-warning-300-rgb:237,131,7;--color-warning-400-rgb:243,143,25;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:255,175,101;--color-warning-700-rgb:255,188,126;--color-warning-800-rgb:255,210,169;--color-warning-900-rgb:255,236,219;--color-warning-950-rgb:255,244,234;--color-danger-50:#470808;--color-danger-100:#a20606;--color-danger-200:#ba1313;--color-danger-300:#d91b1b;--color-danger-400:#fb2b2b;--color-danger-500:#fc5959;--color-danger-600:#ff7c7c;--color-danger-700:#ff9292;--color-danger-800:#ffb1b1;--color-danger-900:#ffd5d5;--color-danger-950:#ffebeb;--color-danger-50-rgb:71,8,8;--color-danger-100-rgb:162,6,6;--color-danger-200-rgb:186,19,19;--color-danger-300-rgb:217,27,27;--color-danger-400-rgb:251,43,43;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:255,124,124;--color-danger-700-rgb:255,146,146;--color-danger-800-rgb:255,177,177;--color-danger-900-rgb:255,213,213;--color-danger-950-rgb:255,235,235;--color-important-50:#440609;--color-important-100:#611700;--color-important-200:#c83509;--color-important-300:#ff4912;--color-important-400:#ff6f42;--color-important-500:#ff8058;--color-important-600:#ff8c68;--color-important-700:#ffb29b;--color-important-800:#ffcebf;--color-important-900:#ffe2d9;--color-important-950:#fff8f5;--color-important-50-rgb:68,6,9;--color-important-100-rgb:97,23,0;--color-important-200-rgb:200,53,9;--color-important-300-rgb:255,73,18;--color-important-400-rgb:255,111,66;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,140,104;--color-important-700-rgb:255,178,155;--color-important-800-rgb:255,206,191;--color-important-900-rgb:255,226,217;--color-important-950-rgb:255,248,245;--color-special-50:#271560;--color-special-100:#30216e;--color-special-200:#452da5;--color-special-300:#513baa;--color-special-400:#7055df;--color-special-500:#8166ee;--color-special-600:#8a6ff5;--color-special-700:#a38cff;--color-special-800:#c4b6ff;--color-special-900:#e4dff7;--color-special-950:#efecfa;--color-special-50-rgb:39,21,96;--color-special-100-rgb:48,33,110;--color-special-200-rgb:69,45,165;--color-special-300-rgb:81,59,170;--color-special-400-rgb:112,85,223;--color-special-500-rgb:129,102,238;--color-special-600-rgb:138,111,245;--color-special-700-rgb:163,140,255;--color-special-800-rgb:196,182,255;--color-special-900-rgb:228,223,247;--color-special-950-rgb:239,236,250;--color-canvas:#0b0f18;--color-inverse:#fff;--color-surface:#353d57;--color-surface-light:#30394a;--color-surface-strong:#3d4667;--color-fore:#ebedf3;--color-focus:#173db6;--color-link:#59a5ff;--color-link-hover:#3883fa;--color-link-visited:#bcdcff;--color-link-active:#bcdcff;--color-placeholder:#4a577f;--color-border:#353d57;--color-border-strong:#3d4667;--color-border-light:#30394a;--color-canvas-rgb:11,15,24;--color-inverse-rgb:255,255,255;--color-surface-rgb:53,61,87;--color-surface-light-rgb:48,57,74;--color-surface-strong-rgb:61,70,103;--color-fore-rgb:235,237,243;--color-focus-rgb:23,61,182;--color-link-rgb:89,165,255;--color-link-hover-rgb:56,131,250;--color-link-visited-rgb:188,220,255;--color-link-active-rgb:188,220,255;--color-placeholder-rgb:74,87,127;--color-border-rgb:53,61,87;--color-border-strong-rgb:61,70,103;--color-border-light-rgb:48,57,74}.light-in-dark{--color-gray-50:#fcfdfe;--color-gray-100:#eff1f3;--color-gray-200:#ebedf3;--color-gray-300:#d2d6e5;--color-gray-400:#b2b9c5;--color-gray-500:#64758b;--color-gray-600:#4a577f;--color-gray-700:#3d4667;--color-gray-800:#353d57;--color-gray-900:#30394a;--color-gray-950:#0b0f18;--color-gray-50-rgb:252,253,254;--color-gray-100-rgb:239,241,243;--color-gray-200-rgb:235,237,243;--color-gray-300-rgb:210,214,229;--color-gray-400-rgb:178,185,197;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:74,87,127;--color-gray-700-rgb:61,70,103;--color-gray-800-rgb:53,61,87;--color-gray-900-rgb:48,57,74;--color-gray-950-rgb:11,15,24;--color-primary-50:#eef6ff;--color-primary-100:#d9eaff;--color-primary-200:#bcdcff;--color-primary-300:#8ec6ff;--color-primary-400:#59a5ff;--color-primary-500:#3883fa;--color-primary-600:#2b67e5;--color-primary-700:#144ce1;--color-primary-800:#173db6;--color-primary-900:#19388f;--color-primary-950:#142457;--color-primary-50-rgb:238,246,255;--color-primary-100-rgb:217,234,255;--color-primary-200-rgb:188,220,255;--color-primary-300-rgb:142,198,255;--color-primary-400-rgb:89,165,255;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:43,103,229;--color-primary-700-rgb:20,76,225;--color-primary-800-rgb:23,61,182;--color-primary-900-rgb:25,56,143;--color-primary-950-rgb:20,36,87;--color-secondary-50:#e7f6ff;--color-secondary-100:#cdecff;--color-secondary-200:#9bd9ff;--color-secondary-300:#77cbff;--color-secondary-400:#60c2ff;--color-secondary-500:#37b2fe;--color-secondary-600:#18a6fd;--color-secondary-700:#1099ed;--color-secondary-800:#078ada;--color-secondary-900:#046bab;--color-secondary-950:#062a4b;--color-secondary-50-rgb:231,246,255;--color-secondary-100-rgb:205,236,255;--color-secondary-200-rgb:155,217,255;--color-secondary-300-rgb:119,203,255;--color-secondary-400-rgb:96,194,255;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:24,166,253;--color-secondary-700-rgb:16,153,237;--color-secondary-800-rgb:7,138,218;--color-secondary-900-rgb:4,107,171;--color-secondary-950-rgb:6,42,75;--color-success-50:#effaf6;--color-success-100:#d6f2e7;--color-success-200:#ade5ce;--color-success-300:#83d7b6;--color-success-400:#5aca9d;--color-success-500:#31bd85;--color-success-600:#2ba675;--color-success-700:#28996c;--color-success-800:#21805a;--color-success-900:#185e3b;--color-success-950:#0e3421;--color-success-50-rgb:239,250,246;--color-success-100-rgb:214,242,231;--color-success-200-rgb:173,229,206;--color-success-300-rgb:131,215,182;--color-success-400-rgb:90,202,157;--color-success-500-rgb:49,189,133;--color-success-600-rgb:43,166,117;--color-success-700-rgb:40,153,108;--color-success-800-rgb:33,128,90;--color-success-900-rgb:24,94,59;--color-success-950-rgb:14,52,33;--color-warning-50:#fff4ea;--color-warning-100:#ffecdb;--color-warning-200:#ffd2a9;--color-warning-300:#ffbc7e;--color-warning-400:#ffaf65;--color-warning-500:#ff9f46;--color-warning-600:#f38f19;--color-warning-700:#ed8307;--color-warning-800:#d17100;--color-warning-900:#af5f01;--color-warning-950:#441506;--color-warning-50-rgb:255,244,234;--color-warning-100-rgb:255,236,219;--color-warning-200-rgb:255,210,169;--color-warning-300-rgb:255,188,126;--color-warning-400-rgb:255,175,101;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:243,143,25;--color-warning-700-rgb:237,131,7;--color-warning-800-rgb:209,113,0;--color-warning-900-rgb:175,95,1;--color-warning-950-rgb:68,21,6;--color-danger-50:#ffebeb;--color-danger-100:#ffd5d5;--color-danger-200:#ffb1b1;--color-danger-300:#ff9292;--color-danger-400:#ff7c7c;--color-danger-500:#fc5959;--color-danger-600:#fb2b2b;--color-danger-700:#d91b1b;--color-danger-800:#ba1313;--color-danger-900:#a20606;--color-danger-950:#470808;--color-danger-50-rgb:255,235,235;--color-danger-100-rgb:255,213,213;--color-danger-200-rgb:255,177,177;--color-danger-300-rgb:255,146,146;--color-danger-400-rgb:255,124,124;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:251,43,43;--color-danger-700-rgb:217,27,27;--color-danger-800-rgb:186,19,19;--color-danger-900-rgb:162,6,6;--color-danger-950-rgb:71,8,8;--color-important-50:#fff8f5;--color-important-100:#ffe2d9;--color-important-200:#ffcebf;--color-important-300:#ffb29b;--color-important-400:#ff8c68;--color-important-500:#ff8058;--color-important-600:#ff6f42;--color-important-700:#ff4912;--color-important-800:#c83509;--color-important-900:#611700;--color-important-950:#440609;--color-important-50-rgb:255,248,245;--color-important-100-rgb:255,226,217;--color-important-200-rgb:255,206,191;--color-important-300-rgb:255,178,155;--color-important-400-rgb:255,140,104;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,111,66;--color-important-700-rgb:255,73,18;--color-important-800-rgb:200,53,9;--color-important-900-rgb:97,23,0;--color-important-950-rgb:68,6,9;--color-special-50:#efecfa;--color-special-100:#e4dff7;--color-special-200:#c4b6ff;--color-special-300:#a38cff;--color-special-400:#8a6ff5;--color-special-500:#8166ee;--color-special-600:#7055df;--color-special-700:#513baa;--color-special-800:#452da5;--color-special-900:#30216e;--color-special-950:#271560;--color-special-50-rgb:239,236,250;--color-special-100-rgb:228,223,247;--color-special-200-rgb:196,182,255;--color-special-300-rgb:163,140,255;--color-special-400-rgb:138,111,245;--color-special-500-rgb:129,102,238;--color-special-600-rgb:112,85,223;--color-special-700-rgb:81,59,170;--color-special-800-rgb:69,45,165;--color-special-900-rgb:48,33,110;--color-special-950-rgb:39,21,96;--color-inherit:inherit;--color-transparent:transparent;--color-current:currentColor;--color-black:#000;--color-white:#fff;--color-canvas:#fff;--color-canvas-light:#fff;--color-canvas-dark:#fcfdfe;--color-inverse:#000;--color-surface:#eff1f3;--color-surface-light:#fcfdfe;--color-surface-strong:#ebedf3;--color-fore:#30394a;--color-fore-in-light:#30394a;--color-fore-in-dark:#fff;--color-focus:#bcdcff;--color-link:#2b47a2;--color-link-hover:#144ce1;--color-link-visited:#6328a4;--color-link-active:#144ce1;--color-placeholder:#64758b;--color-border:#ebedf3;--color-border-strong:#d2d6e5;--color-border-light:#eff1f3;--color-black-rgb:0,0,0;--color-white-rgb:255,255,255;--color-canvas-rgb:255,255,255;--color-canvas-light-rgb:255,255,255;--color-canvas-dark-rgb:252,253,254;--color-inverse-rgb:0,0,0;--color-surface-rgb:239,241,243;--color-surface-light-rgb:252,253,254;--color-surface-strong-rgb:235,237,243;--color-fore-rgb:48,57,74;--color-fore-in-light-rgb:48,57,74;--color-fore-in-dark-rgb:255,255,255;--color-focus-rgb:188,220,255;--color-link-rgb:43,71,162;--color-link-hover-rgb:20,76,225;--color-link-visited-rgb:99,40,164;--color-link-active-rgb:20,76,225;--color-placeholder-rgb:100,117,139;--color-border-rgb:235,237,243;--color-border-strong-rgb:210,214,229;--color-border-light-rgb:239,241,243}body{--btn-bg:var(--color-gray-50)}@media (prefers-color-scheme:dark){.dark-auto{--color-gray-50:#0b0f18;--color-gray-100:#30394a;--color-gray-200:#353d57;--color-gray-300:#3d4667;--color-gray-400:#4a577f;--color-gray-500:#64758b;--color-gray-600:#b2b9c5;--color-gray-700:#d2d6e5;--color-gray-800:#ebedf3;--color-gray-900:#eff1f3;--color-gray-950:#fcfdfe;--color-gray-50-rgb:11,15,24;--color-gray-100-rgb:48,57,74;--color-gray-200-rgb:53,61,87;--color-gray-300-rgb:61,70,103;--color-gray-400-rgb:74,87,127;--color-gray-500-rgb:100,117,139;--color-gray-600-rgb:178,185,197;--color-gray-700-rgb:210,214,229;--color-gray-800-rgb:235,237,243;--color-gray-900-rgb:239,241,243;--color-gray-950-rgb:252,253,254;--color-primary-50:#142457;--color-primary-100:#19388f;--color-primary-200:#173db6;--color-primary-300:#144ce1;--color-primary-400:#2b67e5;--color-primary-500:#3883fa;--color-primary-600:#59a5ff;--color-primary-700:#8ec6ff;--color-primary-800:#bcdcff;--color-primary-900:#d9eaff;--color-primary-950:#eef6ff;--color-primary-50-rgb:20,36,87;--color-primary-100-rgb:25,56,143;--color-primary-200-rgb:23,61,182;--color-primary-300-rgb:20,76,225;--color-primary-400-rgb:43,103,229;--color-primary-500-rgb:56,131,250;--color-primary-600-rgb:89,165,255;--color-primary-700-rgb:142,198,255;--color-primary-800-rgb:188,220,255;--color-primary-900-rgb:217,234,255;--color-primary-950-rgb:238,246,255;--color-secondary-50:#062a4b;--color-secondary-100:#046bab;--color-secondary-200:#078ada;--color-secondary-300:#1099ed;--color-secondary-400:#18a6fd;--color-secondary-500:#37b2fe;--color-secondary-600:#60c2ff;--color-secondary-700:#77cbff;--color-secondary-800:#9bd9ff;--color-secondary-900:#cdecff;--color-secondary-950:#e7f6ff;--color-secondary-50-rgb:6,42,75;--color-secondary-100-rgb:4,107,171;--color-secondary-200-rgb:7,138,218;--color-secondary-300-rgb:16,153,237;--color-secondary-400-rgb:24,166,253;--color-secondary-500-rgb:55,178,254;--color-secondary-600-rgb:96,194,255;--color-secondary-700-rgb:119,203,255;--color-secondary-800-rgb:155,217,255;--color-secondary-900-rgb:205,236,255;--color-secondary-950-rgb:231,246,255;--color-success-50:#0e3421;--color-success-100:#185e3b;--color-success-200:#21805a;--color-success-300:#28996c;--color-success-400:#2ba675;--color-success-500:#31bd85;--color-success-600:#5aca9d;--color-success-700:#83d7b6;--color-success-800:#ade5ce;--color-success-900:#d6f2e7;--color-success-950:#effaf6;--color-success-50-rgb:14,52,33;--color-success-100-rgb:24,94,59;--color-success-200-rgb:33,128,90;--color-success-300-rgb:40,153,108;--color-success-400-rgb:43,166,117;--color-success-500-rgb:49,189,133;--color-success-600-rgb:90,202,157;--color-success-700-rgb:131,215,182;--color-success-800-rgb:173,229,206;--color-success-900-rgb:214,242,231;--color-success-950-rgb:239,250,246;--color-warning-50:#441506;--color-warning-100:#af5f01;--color-warning-200:#d17100;--color-warning-300:#ed8307;--color-warning-400:#f38f19;--color-warning-500:#ff9f46;--color-warning-600:#ffaf65;--color-warning-700:#ffbc7e;--color-warning-800:#ffd2a9;--color-warning-900:#ffecdb;--color-warning-950:#fff4ea;--color-warning-50-rgb:68,21,6;--color-warning-100-rgb:175,95,1;--color-warning-200-rgb:209,113,0;--color-warning-300-rgb:237,131,7;--color-warning-400-rgb:243,143,25;--color-warning-500-rgb:255,159,70;--color-warning-600-rgb:255,175,101;--color-warning-700-rgb:255,188,126;--color-warning-800-rgb:255,210,169;--color-warning-900-rgb:255,236,219;--color-warning-950-rgb:255,244,234;--color-danger-50:#470808;--color-danger-100:#a20606;--color-danger-200:#ba1313;--color-danger-300:#d91b1b;--color-danger-400:#fb2b2b;--color-danger-500:#fc5959;--color-danger-600:#ff7c7c;--color-danger-700:#ff9292;--color-danger-800:#ffb1b1;--color-danger-900:#ffd5d5;--color-danger-950:#ffebeb;--color-danger-50-rgb:71,8,8;--color-danger-100-rgb:162,6,6;--color-danger-200-rgb:186,19,19;--color-danger-300-rgb:217,27,27;--color-danger-400-rgb:251,43,43;--color-danger-500-rgb:252,89,89;--color-danger-600-rgb:255,124,124;--color-danger-700-rgb:255,146,146;--color-danger-800-rgb:255,177,177;--color-danger-900-rgb:255,213,213;--color-danger-950-rgb:255,235,235;--color-important-50:#440609;--color-important-100:#611700;--color-important-200:#c83509;--color-important-300:#ff4912;--color-important-400:#ff6f42;--color-important-500:#ff8058;--color-important-600:#ff8c68;--color-important-700:#ffb29b;--color-important-800:#ffcebf;--color-important-900:#ffe2d9;--color-important-950:#fff8f5;--color-important-50-rgb:68,6,9;--color-important-100-rgb:97,23,0;--color-important-200-rgb:200,53,9;--color-important-300-rgb:255,73,18;--color-important-400-rgb:255,111,66;--color-important-500-rgb:255,128,88;--color-important-600-rgb:255,140,104;--color-important-700-rgb:255,178,155;--color-important-800-rgb:255,206,191;--color-important-900-rgb:255,226,217;--color-important-950-rgb:255,248,245;--color-special-50:#271560;--color-special-100:#30216e;--color-special-200:#452da5;--color-special-300:#513baa;--color-special-400:#7055df;--color-special-500:#8166ee;--color-special-600:#8a6ff5;--color-special-700:#a38cff;--color-special-800:#c4b6ff;--color-special-900:#e4dff7;--color-special-950:#efecfa;--color-special-50-rgb:39,21,96;--color-special-100-rgb:48,33,110;--color-special-200-rgb:69,45,165;--color-special-300-rgb:81,59,170;--color-special-400-rgb:112,85,223;--color-special-500-rgb:129,102,238;--color-special-600-rgb:138,111,245;--color-special-700-rgb:163,140,255;--color-special-800-rgb:196,182,255;--color-special-900-rgb:228,223,247;--color-special-950-rgb:239,236,250;--color-canvas:#0b0f18;--color-inverse:#fff;--color-surface:#353d57;--color-surface-light:#30394a;--color-surface-strong:#3d4667;--color-fore:#ebedf3;--color-focus:#173db6;--color-link:#59a5ff;--color-link-hover:#3883fa;--color-link-visited:#bcdcff;--color-link-active:#bcdcff;--color-placeholder:#4a577f;--color-border:#353d57;--color-border-strong:#3d4667;--color-border-light:#30394a;--color-canvas-rgb:11,15,24;--color-inverse-rgb:255,255,255;--color-surface-rgb:53,61,87;--color-surface-light-rgb:48,57,74;--color-surface-strong-rgb:61,70,103;--color-fore-rgb:235,237,243;--color-focus-rgb:23,61,182;--color-link-rgb:89,165,255;--color-link-hover-rgb:56,131,250;--color-link-visited-rgb:188,220,255;--color-link-active-rgb:188,220,255;--color-placeholder-rgb:74,87,127;--color-border-rgb:53,61,87;--color-border-strong-rgb:61,70,103;--color-border-light-rgb:48,57,74}}*,:after,:before{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity))}:focus-visible{outline-color:transparent}*,:after,:before{--tw-border-spacing-x:0;--tw-border-spacing-y:0;--tw-translate-x:0;--tw-translate-y:0;--tw-rotate:0;--tw-skew-x:0;--tw-skew-y:0;--tw-scale-x:1;--tw-scale-y:1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness:proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-color:rgba(59,130,246,.5);--tw-ring-offset-shadow:0 0 #0000;--tw-ring-shadow:0 0 #0000;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }::backdrop{--tw-border-spacing-x:0;--tw-border-spacing-y:0;--tw-translate-x:0;--tw-translate-y:0;--tw-rotate:0;--tw-skew-x:0;--tw-skew-y:0;--tw-scale-x:1;--tw-scale-y:1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness:proximity;--tw-gradient-from-position: ;--tw-gradient-via-position: ;--tw-gradient-to-position: ;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-color:rgba(59,130,246,.5);--tw-ring-offset-shadow:0 0 #0000;--tw-ring-shadow:0 0 #0000;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: ;--tw-contain-size: ;--tw-contain-layout: ;--tw-contain-paint: ;--tw-contain-style: }html{font-size:var(--font-size-root)}body{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));font-size:.8125rem;line-height:1.5384615385}.dark,body{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}:root{--font-h1-size:2.25rem;--article-p-space:0.5em;--article-heading-space:0.5em;--article-hr-space:1.5em;--article-cell-padding:0.25rem 0.75rem}a,a.disabled:hover{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity))}a:hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}a:focus-visible{outline-color:rgb(var(--color-focus-rgb));outline-offset:2px;outline-width:2px}.code,code{background-color:rgba(var(--color-important-500-rgb),.1);border-radius:var(--radius);padding-left:.25rem;padding-right:.25rem;--tw-text-opacity:1;color:rgba(var(--color-important-500-rgb),var(--tw-text-opacity))}pre{font-size:.75rem;line-height:1rem;overflow:auto;padding:.5rem}pre code{background-color:transparent;color:inherit;padding:0}samp,var{font-weight:700}.blockquote,blockquote{border-left-width:4px;font-size:.875rem;line-height:1.3rem;padding-left:.75rem;text-wrap:balance}.blockquote figcaption,blockquote figcaption{font-size:.75rem;line-height:1rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.h1,.h2,.h3,.h4,.h5,.h6,h1,h2,h3,h4,h5,h6{font-weight:700;line-height:1.5;text-wrap:balance}.h1,h1{font-size:1.75rem}.h2,h2{font-size:1.5rem}.h3,h3{font-size:1.25rem}.h4,h4{font-size:1rem}.h5,h5{font-size:.875rem}.h6,h6{font-size:.75rem}ul{list-style-type:disc}ol,ul{padding-left:1.5em}ol{list-style-type:decimal}dt{font-weight:700}dd{padding-left:2em}.article{color:var(--font-size-article);-webkit-hyphens:auto;hyphens:auto;overflow-wrap:break-word}.article h1,.article h2,.article h3,.article h4{margin-bottom:var(--article-heading-space);margin-top:var(--article-heading-space)}.article audio,.article blockquote,.article figure,.article img,.article ol,.article p,.article table,.article ul,.article video{margin-bottom:var(--article-p-space);margin-top:var(--article-p-space)}.article p{min-height:1em}.article p:empty:before{content:" ";display:inline-block}.article hr{margin-bottom:var(--article-hr-space);margin-top:var(--article-hr-space)}.article table{border-width:1px}.article td,.article th{border-bottom-width:1px;padding:var(--article-cell-padding)}.article thead{background-color:var(--table-head-bg,var(--color-gray-100))}.article ol *,.article table *,.article ul *{margin-bottom:0;margin-top:0}.article pre{border-radius:var(--radius);border-width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity))}:root{--alert-bg:var(--color-surface)}.alert{align-items:center;background-color:var(--alert-bg);border-radius:var(--radius);display:flex;gap:.75rem;padding:.5rem .75rem}.alert-content{display:flex;flex:1 1 auto;flex-direction:column;gap:1rem}.alert-close{margin-bottom:-.375rem;margin-right:-.5rem;margin-top:-.375rem}.alert-link{color:inherit;font-weight:700}.alert-link:hover{color:inherit;text-decoration-line:underline}.alert-heading{font-weight:700;margin:0}.alert-text{flex:1 1 auto;white-space:pre-line}.alert-actions{align-items:center;display:flex;gap:.5rem}:root{--breadcrumb-divider:"/";--breadcrumb-divider-color:var(--color-gray-500);--breadcrumb-color-active:var(--color-gray-500)}.breadcrumb{display:flex;gap:1.25rem;list-style-type:none;padding-left:0}.breadcrumb>li{position:relative}.breadcrumb>li+li:before{color:var(--breadcrumb-divider-color);content:var(--breadcrumb-divider);display:block;left:-1.25rem;position:absolute;text-align:center;width:1.25rem}.breadcrumb>.active{color:var(--breadcrumb-color-active)}:root{--btn-radius:var(--radius);--btn-bg:var(--color-surface);--btn-border-color:var(--color-gray-300);--btn-height:2rem}.btn{align-items:center;background-color:var(--btn-bg);border-radius:var(--btn-radius);display:inline-flex;gap:.375rem;height:var(--btn-height);justify-content:center;padding-left:.75rem;padding-right:.75rem;white-space:nowrap;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--btn-border-color)}.btn,.btn-default:hover{color:inherit}.btn-link{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity));text-decoration-line:underline;text-underline-offset:2px;--tw-ring-color:transparent}.btn-link:visited{color:rgba(var(--color-link-visited-rgb),var(--tw-text-opacity))}.btn-link:hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}.btn-link{--btn-bg:transparent}.btn.size-xs,.size-xs>.btn{padding-left:.25rem;padding-right:.25rem;--btn-height:1.25rem}.btn.size-sm,.btn.size-xs,.size-sm>.btn,.size-xs>.btn{font-size:.75rem;line-height:1rem}.btn.size-sm,.size-sm>.btn{--btn-height:1.5rem}.btn.size-md,.btn.size-sm,.size-md>.btn,.size-sm>.btn{padding-left:.5rem;padding-right:.5rem}.btn.size-md,.size-md>.btn{--btn-height:1.75rem}.btn.size-lg,.size-lg>.btn{font-size:1rem;line-height:1.5rem;padding-left:1rem;padding-right:1rem;--btn-height:2.5rem}.btn.size-xl,.size-xl>.btn{font-size:1.125rem;line-height:1.75rem;padding-left:1.25rem;padding-right:1.25rem;--btn-height:3rem}.btn.square{aspect-ratio:1/1;gap:.125rem;padding-left:0;padding-right:0}@supports not (aspect-ratio:1/1){.btn.square{width:var(--btn-height)}}.btn.btn-caret{padding-left:.25rem;padding-right:.25rem}.btn.btn-wide{min-width:80px}:root{--checkbox-size:12px;--checkbox-color:var(--color-primary-500)}.checkbox,.radio{align-items:center;cursor:pointer;display:flex;gap:.375rem;min-height:20px}.checkbox>input[type=checkbox],.radio>input[type=radio]{accent-color:rgb(var(--color-primary-500-rgb));border-radius:var(--radius-lg)}.checkbox-primary,.radio-primary{display:flex;gap:.375rem;min-height:20px;position:relative}.checkbox-primary>input[type=checkbox],.radio-primary>input[type=radio]{bottom:0;left:0;opacity:0;position:absolute;right:0;top:0}.checkbox-primary>label,.radio-primary>label{cursor:pointer;padding-left:calc(var(--checkbox-size) + 8px);position:relative}.checkbox-primary>label:after,.checkbox-primary>label:before,.radio-primary>label:after,.radio-primary>label:before{display:block;height:var(--checkbox-size);left:0;position:absolute;transition-duration:.15s;transition-property:transform,background-color,color,opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:var(--checkbox-size);--tw-content:"";content:var(--tw-content);top:calc((20px - var(--checkbox-size))/2)}.checkbox-primary>label:before{border-radius:var(--radius-sm);border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.checkbox-primary>label:after{--tw-scale-x:.9;--tw-scale-y:.9;background-image:url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHZpZXdCb3g9IjAgMCAyNCAyNCI+PHBhdGggZmlsbD0iI2ZmZiIgZD0ibTkgMjAuNDItNi4yMS02LjIxIDIuODMtMi44M0w5IDE0Ljc3bDkuODgtOS44OSAyLjgzIDIuODN6Ii8+PC9zdmc+");transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.radio-primary>label:before{border-radius:var(--radius-full);border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.radio-primary>label:after{background-color:var(--checkbox-color);border-radius:var(--radius-full);opacity:0;--checkbox-radio-size:calc(var(--checkbox-size)*2/3);height:var(--checkbox-radio-size);left:calc((var(--checkbox-size) - var(--checkbox-radio-size))/2);top:calc((20px - var(--checkbox-radio-size))/2);width:var(--checkbox-radio-size)}.checkbox-primary>label:hover:before,.radio-primary>label:hover:before{border-color:var(--checkbox-color)}.checkbox-primary.focus>label:before,.checkbox-primary>input[type=checkbox]:focus+label:before,.radio-primary.focus>label:before,.radio-primary>input[type=radio]:focus+label:before{border-color:var(--checkbox-color);outline-color:rgb(var(--color-focus-rgb));outline-style:solid;outline-width:2px}.checkbox-primary.checked>label:before,.checkbox-primary>input[type=checkbox]:checked+label:before{background-color:var(--checkbox-color);border-color:var(--checkbox-color)}.radio-primary.checked>label:before,.radio-primary>input[type=radio]:checked+label:before{border-color:var(--checkbox-color)}.checkbox-primary.checked>label:after,.checkbox-primary>input[type=checkbox]:checked+label:after,.radio-primary.checked>label:after,.radio-primary>input[type=radio]:checked+label:after{opacity:1}.checkbox-primary.disabled>label,.checkbox-primary>input[type=checkbox]:disabled+label,.radio-primary.disabled>label,.radio-primary>input[type=radio]:disabled+label{cursor:not-allowed;opacity:.7;pointer-events:none;--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.checkbox-primary.indeterminate>label:after,.checkbox-primary>input[type=checkbox]:indeterminate+label:after{--tw-border-opacity:1;background-color:var(--checkbox-color);background-image:none;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity));border-width:calc((var(--checkbox-size) - 2px)/2) 2px;opacity:1}.check-list{align-items:flex-start;flex-direction:column;gap:.5rem}.check-list,.check-list-inline{display:flex;padding-bottom:.375rem;padding-top:.375rem}.check-list-inline{align-items:center;-moz-column-gap:1rem;column-gap:1rem;flex-direction:row;flex-wrap:wrap;row-gap:.5rem}.switch{display:flex;gap:.375rem;min-height:20px;padding-left:2.5rem;position:relative}.switch>input{bottom:0;left:0;opacity:0;position:absolute;right:0;top:0}.switch>label:after,.switch>label:before{border-radius:var(--radius-full);border-width:1px;height:1rem;left:0;position:absolute;top:.125rem;width:2rem;--tw-border-opacity:1;border-color:rgba(var(--color-border-strong-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));transition-duration:.3s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:"";content:var(--tw-content)}.switch>label:before{cursor:pointer;--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.switch>label:hover:before{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity))}.switch>label:after{height:.75rem;left:.125rem;top:.25rem;width:.75rem;--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.switch>input:checked+label:before{background-color:var(--checkbox-color);border-color:rgba(var(--color-inverse-rgb),.2)}.switch>input:checked+label:after{color:var(--checkbox-color);left:18px}.switch.focus>label:before,.switch>input:focus+label:before{border-color:var(--checkbox-color);outline-color:rgb(var(--color-focus-rgb));outline-style:solid;outline-width:2px}.switch.disabled>label:before,.switch>input:disabled+label:before{cursor:not-allowed;opacity:.7;pointer-events:none;--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}:root{--form-control-radius:var(--radius);--form-control-border:var(--color-border);--form-control-focus:var(--color-primary-500);--form-control-disabled:var(--color-surface);--form-control-readonly:var(--color-surface)}.dark{--form-control-border:var(--color-border-strong)}input::-moz-placeholder,textarea::-moz-placeholder{--tw-placeholder-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-placeholder-opacity))}input::placeholder,textarea::placeholder{--tw-placeholder-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-placeholder-opacity))}.form-control{border-radius:var(--form-control-radius);display:block;height:2rem;width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));outline-color:transparent;outline-style:solid;outline-width:1px;padding:.25rem .5rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--form-control-border);transition-duration:.15s;transition-property:outline,box-shadow;transition-timing-function:cubic-bezier(.4,0,.2,1)}.form-control.focus,.form-control:focus{outline-color:var(--form-control-focus);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-focus-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.3}.form-control.disabled,.form-control[disabled]{background-color:var(--form-control-disabled);opacity:1}.form-control.readonly,.form-control[readonly]{background-color:var(--form-control-readonly)}select{-webkit-appearance:none;background-image:url("data:image/gif;base64,R0lGODlhBwAEAIAAAMvQ2////yH5BAEAAAEALAAAAAAHAAQAAAIIhA+BGWoNWSgAOw==");background-position:right 8px top 50%;background-repeat:no-repeat;background-size:8px auto;padding-right:1rem}select.form-control[multiple]{background-image:none}textarea.form-control{height:auto;min-height:32px}input[type=file].form-control{padding:.125rem}input[type=file].form-control::-webkit-file-upload-button{-webkit-appearance:none;appearance:none;border-radius:inherit;border-style:none;cursor:pointer;height:1.75rem;padding-left:.5rem;padding-right:.5rem}input[type=file].form-control::-webkit-file-upload-button:hover{background-color:rgba(var(--color-black-rgb),.1)}.has-error .form-control,.has-error.form-control{--tw-ring-color:rgba(var(--color-danger-500-rgb),0.6)}.has-error .form-control.focus,.has-error .form-control:focus,.has-error.form-control.focus,.has-error.form-control:focus{outline-color:rgb(var(--color-danger-500-rgb));--tw-ring-color:rgba(var(--color-danger-500-rgb),0.1)}.has-warning .form-control,.has-warning.form-control{--tw-ring-color:rgba(var(--color-warning-500-rgb),0.6)}.has-warning .form-control.focus,.has-warning .form-control:focus,.has-warning.form-control.focus,.has-warning.form-control:focus{outline-color:rgb(var(--color-warning-500-rgb));--tw-ring-color:rgba(var(--color-warning-500-rgb),0.2)}.has-success .form-control,.has-success.form-control{--tw-ring-color:rgba(var(--color-success-500-rgb),0.6)}.has-success .form-control.focus,.has-success .form-control:focus,.has-success.form-control.focus,.has-success.form-control:focus{outline-color:rgb(var(--color-success-500-rgb));--tw-ring-color:rgba(var(--color-success-500-rgb),0.2)}.form-control.size-sm,.size-sm>.form-control{font-size:.75rem;height:1.5rem;line-height:1rem;padding-left:.5rem;padding-right:.5rem}.form-control.size-md,.size-md>.form-control{height:1.75rem;padding-left:.5rem;padding-right:.5rem}.form-control.size-lg,.size-lg>.form-control{font-size:1rem;height:2.5rem;line-height:1.5rem;padding-left:.75rem;padding-right:.75rem}:root{--input-group-addon-bg:var(--color-gray-50)}.input-group{align-items:stretch;display:flex}.input-group>.form-control,.input-group>.input-control{flex:1 1 auto;z-index:1}.input-group-addon{align-items:center;background-color:var(--input-group-addon-bg);border-radius:var(--form-control-radius);display:flex;flex:none;height:2rem;padding-left:.5rem;padding-right:.5rem;z-index:0;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--form-control-border)}.size-sm>.input-group-addon{font-size:.75rem;height:1.5rem;line-height:1rem;padding-left:.5rem;padding-right:.5rem}.size-lg>.input-group-addon{font-size:1rem;height:2.5rem;line-height:1.5rem;padding-left:.75rem;padding-right:.75rem}.input-group-control{flex:1 1 auto}.input-group>*+*,.input-group>*+* .form-control{border-bottom-left-radius:var(--radius-none);border-top-left-radius:var(--radius-none)}.input-group>:not(:last-child),.input-group>:not(:last-child) .form-control{border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none)}.input-group .btn:focus-visible,.input-group .form-control:focus{z-index:2}:root{--form-tip-color:var(--color-gray-400);--form-label-color:var(--color-gray-700);--form-horz-label-width:6rem;--form-grid-gap-x:1.25rem;--form-grid-gap-y:.75rem}.form{flex-direction:column;gap:1rem}.form,.form-label{display:flex}.form-label{align-items:center;color:var(--form-label-color);flex-direction:row;gap:.25rem;height:2rem;overflow:hidden;position:relative;text-overflow:ellipsis;white-space:nowrap}.form-label.required:after{content:"*";display:inline-block;margin-left:.25rem;--tw-translate-y:0.125rem;--tw-scale-x:1.25;--tw-scale-y:1.25;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.no-required .form-label.required:after{display:none}.form-label-actions{flex:1 1 auto;justify-content:flex-end}.form-label>.checkbox-primary{margin-left:.75rem}.form-tip{color:var(--form-tip-color);display:block;margin-top:.25rem}.has-error .form-tip{--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.has-warning .form-tip{--tw-text-opacity:1;color:rgba(var(--color-warning-500-rgb),var(--tw-text-opacity))}.has-success .form-tip{--tw-text-opacity:1;color:rgba(var(--color-success-500-rgb),var(--tw-text-opacity))}.form-actions{display:flex;flex-direction:row;gap:1rem;justify-content:center}.form-grid{--form-grid-gap-x-half:calc(var(--form-grid-gap-x)/2);--form-grid-gap-y-half:calc(var(--form-grid-gap-y)/2);align-items:flex-start;flex-direction:row;flex-wrap:wrap;gap:0}.form-grid .form-group{padding:var(--form-grid-gap-y-half) var(--form-grid-gap-x-half)}.form-grid .form-label.required:after{margin-left:.25rem;order:-9999}.form-grid .form-label .checkbox{margin-left:.75rem;margin-right:.75rem}.form-grid .has-wrap-after:after{display:block;width:100%;--tw-content:"";content:var(--tw-content)}.form-grid-wrap{width:100%}.form-grid-row{display:flex;flex-direction:row;padding-bottom:var(--form-grid-gap-y-half);padding-top:var(--form-grid-gap-y-half);position:relative;width:100%}.form-grid-col{padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half)}.form-grid .form-actions{gap:1.5rem;justify-content:center;padding:var(--form-grid-gap-y) var(--form-grid-gap-x-half);width:100%}.form-grid .form-actions.is-pinned{border-top-width:1px}.form-horz .form-row{align-items:flex-start;display:flex;flex-direction:row}.form-horz .form-group{align-items:flex-start;display:flex;flex:none;flex-direction:row;flex-wrap:wrap;min-height:32px;min-width:0;padding-left:var(--form-horz-label-width);position:relative}.form-horz .form-row .form-group{flex:1 1 auto}.form-horz .form-group[class*=" w-"],.form-horz .form-group[class^=w-]{flex:none}.form-horz .form-group>*{min-width:0}.form-horz .form-group.no-label{padding-left:0}.form-horz .form-group.no-label>.check-list-inline{padding-left:1rem;padding-right:1rem}.form-horz .form-label{justify-content:flex-end;left:0;padding-left:1rem;padding-right:.5rem;position:absolute;top:0;width:var(--form-horz-label-width)}.form-horz .form-label.required:after{margin-left:0;order:-9999}.form-horz .form-tip{width:100%}.form-horz .form-tip,.form-horz .input-control,.form-horz .input-group{flex:1 1 auto}.form .form-group-wrapper,.form-horz .form-group-wrapper{flex:1 1 auto;min-width:0;width:100%;z-index:1}.form .form-group-wrapper.flex-none,.form-horz .form-group-wrapper.flex-none{flex:none}.form fieldset>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.form fieldset{padding-bottom:1rem;padding-left:1rem}.form-grid fieldset>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.form legend{border-bottom-width:1px;display:flex;justify-content:flex-start;margin-left:-1rem;width:100%;--tw-border-opacity:1;border-bottom-color:rgba(var(--color-primary-100-rgb),var(--tw-border-opacity));width:calc(100% + 1rem)}.form-title{align-items:center;background-color:rgba(var(--color-primary-50-rgb),.5);display:flex;font-weight:700;height:1.75rem;padding-left:.75rem;padding-right:.75rem}:root{--input-control-fix-width-sm:2rem;--input-control-fix-width:4.375rem;--input-control-fix-width-lg:6.75rem}.input-control{position:relative;--input-control-prefix:8px;--input-control-suffix:8px}.input-control-prefix,.input-control-suffix{align-items:center;display:flex;height:100%;left:0;opacity:.5;padding-left:.5rem;padding-right:.5rem;position:absolute;top:0;white-space:nowrap;width:var(--input-control-prefix);z-index:1}.input-control-suffix{justify-content:flex-end;left:auto;right:0;width:var(--input-control-suffix)}.form-control:focus+.input-control-prefix,.form-control:focus+.input-control-suffix{opacity:1}.input-control>.form-control{padding-left:var(--input-control-prefix);padding-right:var(--input-control-suffix)}.input-control>select.form-control{background-position-x:calc(100% - var(--input-control-suffix) - 8px);padding-right:calc(var(--input-control-suffix) + 20px)}.has-prefix{--input-control-prefix:var(--input-control-fix-width)}.has-suffix{--input-control-suffix:var(--input-control-fix-width)}.has-prefix-sm{--input-control-prefix:var(--input-control-fix-width-sm)}.has-suffix-sm{--input-control-suffix:var(--input-control-fix-width-sm)}.has-prefix-lg{--input-control-prefix:var(--input-control-fix-width-lg)}.has-suffix-lg{--input-control-suffix:var(--input-control-fix-width-lg)}.has-prefix-icon{--input-control-prefix:32px}.has-suffix-icon{--input-control-suffix:32px}.input-control.has-prefix-icon{--input-control-prefix:32px}.input-control.has-suffix-icon{--input-control-suffix:32px}.input-control.has-prefix-icon>.input-control-prefix,.input-control.has-suffix-icon>.input-control-suffix{justify-content:center;padding:0}.input-control.size-sm>.form-control,.input-control.size-sm>.input-control-prefix,.input-control.size-sm>.input-control-suffix{font-size:.75rem;line-height:1rem}.input-control.size-lg>.form-control,.input-control.size-lg>.input-control-prefix,.input-control.size-lg>.input-control-suffix{font-size:1rem;line-height:1.5rem}:root{--label-bg:rgba(var(--color-canvas-rgb),.1);--label-border-color:var(--color-gray-300);--label-color:var(--color-gray-500);--label-radius:var(--radius)}.label{align-items:center;background-color:var(--label-bg);border-radius:var(--label-radius);color:var(--label-color);display:inline-flex;font-size:.75rem;height:1.25rem;justify-content:center;line-height:1rem;min-width:1.25rem;padding-left:.25rem;padding-right:.25rem;white-space:pre-line;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:var(--label-border-color)}.label.size-lg{font-size:.8125rem;height:1.5rem;line-height:1.25rem;min-width:1.5rem;padding-left:.5rem;padding-right:.5rem}.label.size-sm{height:1rem;min-width:1rem}.label-dot{aspect-ratio:1/1;border-radius:var(--radius-full);height:.5rem;min-width:0;padding-left:0;padding-right:0}.caret,.caret-down,.caret-left,.caret-right,.caret-up{align-items:center;display:inline-flex;height:.75rem;justify-content:center;position:relative;width:.75rem}.caret-down:before,.caret-left:before,.caret-right:before,.caret-up:before,.caret:before{display:block;height:.35rem;transform-origin:center;width:.35rem;--tw-translate-y:-1px;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.caret-left:before{--tw-translate-x:0.125rem;--tw-translate-y:0px;--tw-rotate:135deg}.caret-left:before,.caret-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.caret-right:before{--tw-translate-x:-0.125rem;--tw-translate-y:0px;--tw-rotate:-45deg}.caret-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:focus>.caret,:hover>.caret{opacity:inherit}.disabled .caret,.readonly .caret{opacity:var(--caret-opacity,.5)}.listitem{align-items:center;border-radius:var(--radius);display:flex;flex-direction:row;flex-wrap:nowrap;gap:.5rem;padding:.25rem}.listitem.selected{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.listitem.active{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.item-actions,.item-avatar,.item-icon,.item-trailing,.item-trailing-icon{flex:none}.item-icon.icon-EMPTY{display:none}.item-subtitle{font-size:.75rem;line-height:1rem;opacity:.8}.item-content,.item-text{flex:1 1 auto;min-width:0}.item-leading,.item-trailing{align-items:center;display:flex;flex:none;gap:.5rem}.item-checkbox{margin-right:-.5rem}.item-content{align-items:center;display:flex;gap:.5rem}.multiline>.item-content{align-items:flex-start;flex-direction:column;gap:.25rem}.list{list-style-type:none;padding-left:0}.list-heading-inner .item-title{font-weight:700;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.with-hover-actions>.item{position:relative}.with-hover-actions>.item>.item-inner .item-actions{opacity:0;pointer-events:none;position:absolute;right:.25rem;top:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.with-hover-actions>.item:hover>.item-inner .item-actions{display:flex;margin-top:-.25rem;opacity:1;pointer-events:auto;position:static}.list.is-nested-sub{padding-left:var(--list-indent)}.is-nested-collapsed{display:none}.nested-toggle-icon{align-items:center;border-radius:var(--radius);display:flex;height:1rem;justify-content:center;margin-right:-.25rem;width:1rem}.magnifier{display:inline-block;height:1em;position:relative;width:1em}.magnifier:after,.magnifier:before{border-radius:var(--radius-full);content:"";display:block;position:absolute}.magnifier:before{border:1px solid;height:.75em;width:.75em}.magnifier:after{height:1px;left:.55em;top:.7em;width:.5em;--tw-rotate:45deg;background-color:currentColor;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.search-box.compact.has-prefix-icon{--input-control-prefix:24px}.search-box.compact.has-suffix-icon{--input-control-suffix:24px}:root{--menu-bg:var(--color-canvas);--menu-active-bg:var(--color-primary-500);--menu-active-color:var(--color-canvas);--menu-selected-bg:var(--color-primary-50);--menu-selected-color:var(--color-primary-500);--menu-icon-opacity:.5;--menu-icon-margin:1.75rem;--menu-min-width:3rem;--menu-heading-color:var(--color-gray-500)}.menu{background:var(--menu-bg);max-width:var(--menu-max-width);min-width:var(--menu-min-width);padding:.5rem}.menu-wrapper{display:flex;flex-direction:column;min-height:0}.menu-wrapper>.menu{flex:1 1 auto;min-height:0;overflow:auto}.menu-item>.item-inner,.menu-item>a{align-items:center;border-radius:var(--radius);color:inherit;cursor:pointer;display:flex;gap:.5rem;justify-content:space-between;overflow:hidden;padding:.25rem .5rem;position:relative;text-overflow:ellipsis;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1);white-space:nowrap}.menu-item>.selected{background:var(--menu-selected-bg);color:var(--menu-selected-color)}.menu-item>.active,.menu-item>a.hover,.menu-item>a:hover{background:var(--menu-active-bg);color:var(--menu-active-color)}.menu-item.disabled>a:hover,.menu-item>a.disabled:hover{background-color:inherit;color:inherit}.menu-item .item-title{flex:1 1 auto;min-width:0;overflow:hidden;text-overflow:clip;white-space:nowrap}.menu>.divider{margin:.25rem}.menu-heading{align-items:center;color:var(--menu-heading-color);display:flex;font-size:.75rem;font-weight:700;height:2rem;line-height:1rem;padding-left:.25rem;padding-right:.25rem}.has-icons>.menu-item>a>.item-icon{align-items:center;display:flex;height:1rem;justify-content:center;opacity:var(--menu-icon-opacity);width:1rem}.menu-nested{--menu-indent:10px}.menu-nested .menu{background-color:transparent;margin-bottom:-.5rem;margin-left:var(--menu-indent);margin-top:-.5rem;padding-right:0}.menu-nested .menu-item>.item-inner{padding-left:0}.menu-nested .search-menu-footer,.menu-nested .search-menu-header{margin-bottom:.25rem;margin-left:var(--menu-indent);margin-top:-.125rem;padding-right:1px}.menu.compact .menu-item>a{padding-bottom:.125rem;padding-top:.125rem}.menu.compact .menu-heading{height:1.75rem}.search-menu-header{padding:.5rem .5rem .125rem}.search-menu-footer{padding:.125rem .5rem .5rem}.search-menu .item.is-not-match,.search-menu-footer:empty,.search-menu-header:empty{display:none}.search-menu .item.is-not-match.has-match-child{display:list-item}.search-menu .item.is-not-match.has-match-child>.item-inner{opacity:.5;pointer-events:none}.search-menu.no-toggle-on-search .nested-toggle-icon{pointer-events:none}.search-menu .is-match-keys{font-weight:700;text-decoration-line:underline}.search-menu-no-match-hint{display:none;font-size:.75rem;line-height:1rem;padding:.5rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.no-match-child .search-menu-no-match-hint{display:block}.no-match-child>.menu{display:none}.search-menu-exceed-limit-hint{font-size:.75rem;line-height:1rem;padding:.5rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}:root{--alert-bg:var(--color-surface)}.alert{align-items:center;background-color:var(--alert-bg);border-radius:var(--radius);display:flex;gap:.75rem;padding:.5rem .75rem}.alert-content{display:flex;flex:1 1 auto;flex-direction:column;gap:1rem}.alert-close{margin-bottom:-.375rem;margin-right:-.5rem;margin-top:-.375rem}.alert-link{color:inherit;font-weight:700}.alert-link:hover{color:inherit;text-decoration-line:underline}.alert-heading{font-weight:700;margin:0}.alert-text{flex:1 1 auto;white-space:pre-line}.alert-actions{align-items:center;display:flex;gap:.5rem}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.messagers{align-items:flex-end;bottom:0;display:flex;flex-direction:column;gap:.5rem;justify-content:flex-end;left:0;padding:1rem;pointer-events:none;position:fixed;right:0;top:0;z-index:1900}.messagers-top-left,.messagers-top-right{justify-content:flex-start}.messagers-bottom-left,.messagers-top-left{align-items:flex-start}.messagers-bottom,.messagers-center,.messagers-top{align-items:center}.messagers-top,.messagers-top-left,.messagers-top-right{justify-content:flex-start}.messagers-center{justify-content:center}.messager{background-color:rgba(var(--color-inverse-rgb),.8);pointer-events:auto;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);transition-duration:.3s}:root{--progress-radius:var(--radius);--progress-striped-size:40px;--progress-bg:var(--color-surface);--progress-bar-color:var(--color-primary-500)}.progress{background:var(--progress-bg);border-radius:var(--progress-radius);display:flex;height:1.25rem}.progress-bar{background:var(--progress-bar-color);height:100%;transition-duration:.5s;transition-property:width;transition-timing-function:cubic-bezier(.4,0,.2,1)}.progress-striped>.progress-bar{background-image:linear-gradient(45deg,rgba(var(--color-canvas-rgb),.15) 25%,transparent 25%,transparent 50%,rgba(var(--color-canvas-rgb),.15) 50%,rgba(var(--color-canvas-rgb),.15) 75%,transparent 75%,transparent);background-size:var(--progress-striped-size) var(--progress-striped-size)}.progress>.progress-bar:first-child{border-bottom-left-radius:inherit;border-top-left-radius:inherit}.progress>.progress-bar:last-child{border-bottom-right-radius:inherit;border-top-right-radius:inherit}.progress.active .progress-bar{animation:progress-bar-stripes 2s linear infinite}@keyframes progress-bar-stripes{0%{background-position:40px 0}to{background-position:0 0}}.scrollbar,:root{--scrollbar-size:10px;--scrollbar-opacity:.6;--scrollbar-bg:rgba(var(--color-inverse-rgb),.15);--scrollbar-inset:inset 0 0 0 1px rgba(var(--color-inverse-rgb),.05);--scrollbar-bar-bg:rgba(var(--color-inverse-rgb),.3);--scrollbar-hover-bg:rgba(var(--color-inverse-rgb),.4);--scrollbar-drag-bg:rgba(var(--color-inverse-rgb),.5);--scrollbar-radius:var(--radius-sm);--scrollbar-duration:.7s}::-webkit-scrollbar{height:var(--scrollbar-size);width:var(--scrollbar-size)}::-webkit-scrollbar-track{box-shadow:var(--scrollbar-shadow);-webkit-transition:background-color var(--scrollbar-duration);transition:background-color var(--scrollbar-duration)}::-webkit-scrollbar-track:hover,:hover::-webkit-scrollbar-track{background:var(--scrollbar-bg)}::-webkit-scrollbar-thumb{background:var(--scrollbar-bar-bg);border-radius:var(--scrollbar-radius);min-height:var(--scrollbar-size);-webkit-transition:var(--scrollbar-duration);transition:var(--scrollbar-duration);-webkit-transition-property:background-color;transition-property:background-color}::-webkit-scrollbar-thumb:hover{background:var(--scrollbar-hover-bg)}::-webkit-scrollbar-thumb:active{background:var(--scrollbar-drag-bg)}@-moz-document url-prefix(){.scrollbar-thin{scrollbar-width:thin}}.scrollbar-thin::-webkit-scrollbar{height:calc(var(--scrollbar-size)/2);width:calc(var(--scrollbar-size)/2)}.scrollbar-hover::-webkit-scrollbar,.scrollbar-hover::-webkit-scrollbar-thumb,.scrollbar-hover::-webkit-scrollbar-track{visibility:hidden}.scrollbar-hover:hover::-webkit-scrollbar,.scrollbar-hover:hover::-webkit-scrollbar-thumb,.scrollbar-hover:hover::-webkit-scrollbar-track{visibility:visible}@font-face{font-family:ZentaoIcon;font-style:normal;font-weight:400;src:url(./icons/ZentaoIcon.eot?v=1.70);src:url(./icons/ZentaoIcon.woff?v=1.70) format("woff"),url(./icons/ZentaoIcon.ttf?v=1.70) format("truetype"),url(./icons/ZentaoIcon.svg?v=1.70#regular) format("svg")}.icon,[class*=" icon-"],[class^=icon-]{display:inline-block;font-display:block;font-family:ZentaoIcon;font-size:14px;font-style:normal;font-variant:normal;font-weight:400;line-height:1;text-transform:none;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.icon:before{display:inline-block;min-width:14px;text-align:center}.icon-xs:before{font-size:.7em}.icon-sm:before{font-size:.8em}.icon-lg:before{font-size:1.25em;vertical-align:-10%}.icon-2x{font-size:28px}.icon-3x{font-size:42px}.icon-4x{font-size:56px}.icon-5x{font-size:70px}.icon-run{position:relative}.icon-run:before{opacity:.5}.icon-run:after{bottom:0;content:"\ea07";display:block;left:0;position:absolute;right:0;text-align:center;top:0}.icon-guihua:before{content:"\ea02"}.icon-memory:before{content:"\e9fd"}.icon-cpu:before{content:"\e9fe"}.icon-pause-pure:before{content:"\e9ff"}.icon-exclamation-pure:before{content:"\ea00"}.icon-zentao:before{content:"\e901"}.icon-zentao-alt:before{content:"\e900"}.icon-safe:before{content:"\ea06"}.icon-ai:before{content:"\e983"}.icon-kanban:before{content:"\e997"}.icon-college:before{content:"\e9c8"}.icon-home:before,.icon-menu-my:before{content:"\e97a"}.icon-program:before{content:"\e9aa"}.icon-lightbulb-alt:before,.icon-product:before{content:"\e98f"}.icon-project:before,.icon-rocket:before{content:"\e99c"}.icon-run:before{content:"\e9a9"}.icon-run-alt:before{content:"\ea07"}.icon-test:before{content:"\e956"}.icon-devops:before,.icon-infinite:before{content:"\e9a3"}.icon-doc:before,.icon-menu-doc:before{content:"\e99b"}.icon-statistic:before{content:"\e999"}.icon-group:before,.icon-menu-users:before,.icon-persons:before,.icon-team:before{content:"\e97e"}.icon-assets:before,.icon-diamond:before{content:"\e9ae"}.icon-flow:before{content:"\e994"}.icon-backend:before,.icon-cog-outline:before{content:"\ea05"}.icon-help:before{content:"\e968"}.icon-download:before,.icon-import:before{content:"\e904"}.icon-export:before{content:"\e905"}.icon-lightbulb:before{content:"\e91c"}.icon-close:before{content:"\e936"}.icon-check:before{content:"\e5ca"}.icon-minus:before{content:"\e926"}.icon-expand-alt:before{content:"\e6f1"}.icon-collapse-alt:before{content:"\e6f2"}.icon-fullscreen:before{content:"\e96b"}.icon-star-empty:before{content:"\e94a"}.icon-star:before{content:"\e94b"}.icon-exclamation-sign:before{content:"\e930"}.icon-info-sign:before{content:"\e9d5"}.icon-flag:before{content:"\e937"}.icon-check-circle:before{content:"\e92f"}.icon-check-sign:before{content:"\e938"}.icon-chart-pie:before{content:"\e95b"}.icon-history:before{content:"\e95f"}.icon-pencil:before{content:"\e254"}.icon-search:before{content:"\e928"}.icon-restart:before{content:"\e95e"}.icon-cog:before{content:"\e93b"}.icon-chart-line:before{content:"\e95c"}.icon-bar-chart:before,.icon-chart-bar:before{content:"\e95d"}.icon-exchange:before{content:"\e927"}.icon-severity:before{content:"\e973"}.icon-book:before{content:"\f02d"}.icon-treemap-alt:before{content:"\e971"}.icon-severity-solid:before{content:"\e902"}.icon-chat-line:before{content:"\e998"}.icon-stack:before{content:"\e943"}.icon-cube:before{content:"\e967"}.icon-minus-sign:before{content:"\e939"}.icon-bars-sign:before{content:"\e93a"}.icon-chat:before,.icon-message:before{content:"\e940"}.icon-more:before{content:"\e744"}.icon-certificate:before{content:"\f0a3"}.icon-bell:before{content:"\e7f5"}.icon-columns:before{content:"\f0db"}.icon-envelope-o:before{content:"\e92a"}.icon-unfold-all:before{content:"\e931"}.icon-fold-all:before{content:"\e932"}.icon-bars:before{content:"\e948"}.icon-cards-view:before{content:"\e949"}.icon-ellipsis-v:before{content:"\e5d4"}.icon-spinner-indicator:before{content:"\e982"}.icon-up-circle:before{content:"\e92b"}.icon-right-circle:before{content:"\e92c"}.icon-down-circle:before{content:"\e92d"}.icon-left-circle:before{content:"\e92e"}.icon-angle-double-right:before{content:"\f101"}.icon-angle-down:before{content:"\e313"}.icon-angle-left:before{content:"\e314"}.icon-angle-right:before{content:"\e315"}.icon-angle-top:before{content:"\e316"}.icon-first-page:before{content:"\e5dc"}.icon-last-page:before{content:"\e5dd"}.icon-caret-down:before{content:"\f0d7"}.icon-caret-up:before{content:"\f0d8"}.icon-caret-left:before{content:"\f0d9"}.icon-caret-right:before{content:"\f0da"}.icon-sort:before{content:"\f0dc"}.icon-sort-down:before{content:"\f0dd"}.icon-sort-up:before{content:"\f0de"}.icon-arrow-up:before{content:"\e923"}.icon-arrow-down:before{content:"\e924"}.icon-arrow-left:before{content:"\e952"}.icon-arrow-right:before{content:"\e93e"}.icon-chevron-left:before{content:"\e934"}.icon-chevron-right:before{content:"\e935"}.icon-chevron-double-up:before{content:"\e959"}.icon-chevron-double-down:before{content:"\e95a"}.icon-folder-account:before{content:"\e942"}.icon-folder-move:before{content:"\e960"}.icon-folder-plus:before{content:"\e961"}.icon-folder-upload:before{content:"\e962"}.icon-folder-star:before{content:"\e963"}.icon-folder-edit:before{content:"\e964"}.icon-folder-download:before{content:"\e965"}.icon-folder-outline:before{content:"\e966"}.icon-folder:before{content:"\e944"}.icon-folder-o:before{content:"\e945"}.icon-folder-open-o:before{content:"\e946"}.icon-folder-open:before{content:"\e947"}.icon-color:before{content:"\e93c"}.icon-paper-clip:before{content:"\e93d"}.icon-text:before{content:"\e929"}.icon-share:before{content:"\f064"}.icon-format-list-bulleted:before{content:"\e9a8"}.icon-format-bold:before{content:"\e953"}.icon-format-header-pound:before{content:"\e954"}.icon-format-italic:before{content:"\e955"}.icon-format-list-numbers:before{content:"\e969"}.icon-format-quote-close:before{content:"\e96a"}.icon-image:before{content:"\e96c"}.icon-table-large:before{content:"\e96d"}.icon-productplan:before{content:"\e9fc"}.icon-aiux:before{content:"\e99e"}.icon-qc:before{content:"\e986"}.icon-qc-q:before{content:"\e985"}.icon-qc-c:before{content:"\e987"}.icon-sonarqube:before{content:"\e9ba"}.icon-board:before{content:"\ea15"}.icon-market:before{content:"\ea01"}.icon-ztool:before{content:"\e9c1"}.icon-contacts:before{content:"\e9c3"}.icon-chats:before{content:"\e9c4"}.icon-ops:before{content:"\e903"}.icon-menu-backend:before{content:"\e993"}.icon-feedback:before{content:"\e991"}.icon-oa:before{content:"\e9a1"}.icon-more-circle:before{content:"\e988"}.icon-controls:before{content:"\e995"}.icon-account:before{content:"\e992"}.icon-about:before,.icon-info:before{content:"\e996"}.icon-exclamation:before{content:"\e9fa"}.icon-exit:before{content:"\e99a"}.icon-theme:before{content:"\e9a0"}.icon-globe:before,.icon-lang:before{content:"\f0ac"}.icon-template:before{content:"\e9fb"}.icon-seal:before{content:"\e9f8"}.icon-menu-arrow-left:before{content:"\e9f0"}.icon-menu-arrow-right:before{content:"\e9f1"}.icon-add-directory:before{content:"\e9ef"}.icon-design:before{content:"\e9ec"}.icon-download-alt:before{content:"\e9ea"}.icon-blame:before{content:"\e9e0"}.icon-draft-edit:before{content:"\e9dc"}.icon-sub-review-user:before{content:"\e9db"}.icon-sub-review:before{content:"\e9df"}.icon-ztf:before{content:"\e9dd"}.icon-save:before{content:"\e9d8"}.icon-list-box:before{content:"\e9b4"}.icon-usecase:before{content:"\e99d"}.icon-code:before{content:"\e990"}.icon-summary:before{content:"\e9ad"}.icon-more-alt:before{content:"\e9a7"}.icon-customer:before{content:"\e9d9"}.icon-alarm:before{content:"\ea16"}.icon-treeview:before{content:"\ea0d"}.icon-or:before{content:"\ea0b"}.icon-manager:before{content:"\ea0c"}.icon-target:before{content:"\ea0a"}.icon-ipd:before{content:"\e9f9"}.icon-wiki-lib:before{content:"\e9f5"}.icon-annex-lib:before{content:"\e9f6"}.icon-interface-lib:before{content:"\e9f7"}.icon-has-authority-pack:before{content:"\e9f3"}.icon-without-authority-pack:before{content:"\e9f4"}.icon-data-structure:before{content:"\e9f2"}.icon-waterfallplus:before{content:"\e9ed"}.icon-agileplus:before{content:"\e9ee"}.icon-horn:before{content:"\e9eb"}.icon-resume:before{content:"\e9e9"}.icon-mirror:before{content:"\e9e6"}.icon-remote:before{content:"\e9e7"}.icon-moon:before{content:"\e9e8"}.icon-ticket:before{content:"\e9e1"}.icon-gantt-alt:before{content:"\e9e2"}.icon-tree:before{content:"\e9c9"}.icon-list:before{content:"\e9cb"}.icon-gantt:before{content:"\e9cc"}.icon-group-view:before{content:"\e9cd"}.icon-inherit-space:before{content:"\e9c2"}.icon-card-archive:before{content:"\e9b8"}.icon-col-archive:before{content:"\e9b9"}.icon-col-add-right:before{content:"\e9bb"}.icon-col-add-left:before{content:"\e9bc"}.icon-col-split:before{content:"\e9bd"}.icon-waterfall:before{content:"\e9a4"}.icon-manual:before{content:"\e98d"}.icon-lane:before{content:"\e9b1"}.icon-mobile:before{content:"\ea18"}.icon-clear:before{content:"\ea19"}.icon-db:before{content:"\ea17"}.icon-unpinned:before{content:"\ea08"}.icon-pinned:before{content:"\ea09"}.icon-support-ticket:before{content:"\ea04"}.icon-snap-house:before{content:"\e9e3"}.icon-wrench:before{content:"\e9e4"}.icon-desktop:before{content:"\e9e5"}.icon-back-circle:before{content:"\e9da"}.icon-back:before{content:"\e9d3"}.icon-shield:before{content:"\e9ca"}.icon-meh:before{content:"\e9ce"}.icon-frown:before{content:"\e9cf"}.icon-smile:before{content:"\e9d0"}.icon-unlock-solid:before{content:"\e9d1"}.icon-lock-solid:before{content:"\e9d2"}.icon-ver:before{content:"\e9c6"}.icon-publish:before,.icon-send:before{content:"\e9c7"}.icon-tag:before{content:"\e9be"}.icon-tag-lock:before{content:"\e9bf"}.icon-code-fork:before{content:"\f126"}.icon-branch-lock:before{content:"\e9c0"}.icon-groups:before{content:"\e9af"}.icon-thumbs-up:before{content:"\f087"}.icon-thumbs-down:before{content:"\f088"}.icon-thumbs-up-solid:before{content:"\e9d6"}.icon-thumbs-down-solid:before{content:"\e9d7"}.icon-hash:before,.icon-version:before{content:"\e9ab"}.icon-p-square:before{content:"\e97b"}.icon-video-play:before{content:"\e97f"}.icon-plus-solid-circle:before{content:"\e974"}.icon-minuse-solid-circle:before{content:"\e9b6"}.icon-s:before{content:"\e975"}.icon-c:before{content:"\e976"}.icon-t:before{content:"\e977"}.icon-guide:before{content:"\e978"}.icon-todo:before{content:"\e979"}.icon-plus:before{content:"\e925"}.icon-side-left:before{content:"\e9b3"}.icon-side-right:before{content:"\e9b2"}.icon-fullscreen-exit:before{content:"\e972"}.icon-alert:before{content:"\e99f"}.icon-undo:before{content:"\e93f"}.icon-redo:before{content:"\e9d4"}.icon-swap:before{content:"\e9b0"}.icon-chat-solid:before{content:"\e9b5"}.icon-clock:before{content:"\e97c"}.icon-cost:before{content:"\e97d"}.icon-pencil-alt:before{content:"\e984"}.icon-size-height:before{content:"\e9c5"}.icon-upload-file:before{content:"\ea03"}.icon-file-log:before{content:"\e9de"}.icon-rich-text:before{content:"\e913"}.icon-markdown:before{content:"\e916"}.icon-excel:before{content:"\e933"}.icon-text-link:before{content:"\e94d"}.icon-ppt:before{content:"\e957"}.icon-word:before{content:"\e958"}.icon-doc-lib:before{content:"\e96f"}.icon-file-empty:before,.icon-file:before{content:"\f016"}.icon-file-text:before{content:"\f0f6"}.icon-file-alt:before{content:"\f15b"}.icon-file-text-alt:before{content:"\f15c"}.icon-file-pdf:before{content:"\f1c1"}.icon-file-word:before{content:"\f1c2"}.icon-file-excel:before{content:"\f1c3"}.icon-file-powerpoint:before{content:"\f1c4"}.icon-file-image:before{content:"\f1c5"}.icon-file-archive:before{content:"\f1c6"}.icon-file-audio:before{content:"\f1c7"}.icon-file-video:before{content:"\f1c8"}.icon-file-code:before{content:"\f1c9"}.icon-multi-input:before{content:"\ea1a"}.icon-cell-input:before{content:"\ea0e"}.icon-input:before{content:"\ea0f"}.icon-checkbox:before{content:"\ea10"}.icon-radio:before{content:"\ea11"}.icon-transition:before{content:"\ea12"}.icon-add-sub-chapter:before{content:"\ea13"}.icon-add-chapter:before{content:"\ea14"}.icon-menu-collapse:before{content:"\e980"}.icon-menu-expand:before{content:"\e981"}.icon-estimate:before{content:"\e9ac"}.icon-sprint:before{content:"\e9a2"}.icon-shield-check:before{content:"\e9a5"}.icon-ok:before{content:"\e9a6"}.icon-printer:before{content:"\e906"}.icon-bullhorn:before{content:"\e910"}.icon-person:before{content:"\e941"}.icon-fields:before{content:"\e989"}.icon-trigger:before{content:"\e98a"}.icon-layout:before{content:"\e98b"}.icon-audit:before{content:"\e98c"}.icon-ban-circle:before,.icon-cancel:before{content:"\e951"}.icon-eye:before{content:"\e94e"}.icon-eye-off:before{content:"\e96e"}.icon-unlock:before{content:"\e94f"}.icon-lock:before,.icon-private:before{content:"\e950"}.icon-move:before{content:"\e94c"}.icon-hand-right:before{content:"\e907"}.icon-checked:before{content:"\e908"}.icon-off:before{content:"\e909"}.icon-play:before,.icon-start:before{content:"\e90a"}.icon-time:before{content:"\e90b"}.icon-edit:before{content:"\e90c"}.icon-trash:before{content:"\e90d"}.icon-link:before{content:"\e90e"}.icon-unlink:before{content:"\e90f"}.icon-bug:before{content:"\e911"}.icon-list-alt:before{content:"\e912"}.icon-alter:before,.icon-change:before{content:"\e970"}.icon-glasses:before,.icon-review:before{content:"\e914"}.icon-sitemap:before,.icon-testcase:before{content:"\e915"}.icon-pluses:before{content:"\e917"}.icon-report-list:before{content:"\e918"}.icon-active:before,.icon-magic:before{content:"\e919"}.icon-treemap:before{content:"\e91a"}.icon-confirm:before{content:"\e91b"}.icon-split:before{content:"\e98e"}.icon-calendar:before,.icon-delay:before{content:"\e91d"}.icon-pause:before{content:"\e91e"}.icon-ban:before{content:"\e91f"}.icon-plus-bold:before{content:"\e920"}.icon-copy:before{content:"\e921"}.icon-refresh:before{content:"\e922"}.icon-diff:before{content:"\e9b7"}.status-active,.status-asked,.status-normal,.status-unconfirmed,.status-wait{color:var(--color-status-normal,#313c52)}.status-active.status-issue,.status-checking,.status-commenting,.status-confirmed,.status-doing{color:#ff6f42}.status-blocked,.status-hangup,.status-pause,.status-suspended{color:#b89664}.status-clarify,.status-draft{color:#8166ee}.status-noreview,.status-reviewing,.status-wait.status-testcase{color:#18a6fd}.status-active.status-risk,.status-changed,.status-changing,.status-fail{color:#fb2b2b}.status-checked,.status-done,.status-pass,.status-replied,.status-resolved,.status-success{color:#0dbb7d}.status-cancel,.status-canceled,.status-investigate{color:var(--color-status-cancel,#838a9d)}.status-closed,.status-testtask.status-done{color:var(--color-status-closed,#9ea3b0)}.dark{--color-status-normal:#eff1f3;--color-status-cancel:#9ea3b0;--color-status-closed:#838a9d}@media (prefers-color-scheme:dark){.dark-auto{--color-status-normal:#eff1f3;--color-status-cancel:#9ea3b0;--color-status-closed:#838a9d}}.pri,[class*=" pri-"],[class^=pri-]{border-color:currentColor;border-radius:var(--radius-full);border-width:1px;display:inline-block;font-size:.75rem;height:1rem;line-height:1rem;line-height:14px;max-width:54px;min-width:16px;overflow:hidden;padding-left:.125rem;padding-right:.125rem;text-align:center;white-space:nowrap;--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.pri-1{color:rgb(255 73 18/var(--tw-text-opacity))}.pri-1,.pri-2{--tw-text-opacity:1}.pri-2{color:rgba(var(--color-warning-600-rgb),var(--tw-text-opacity))}.pri-3{color:rgb(59 130 246/var(--tw-text-opacity))}.pri-3,.pri-4{--tw-text-opacity:1}.pri-4{color:rgb(149 211 224/var(--tw-text-opacity))}.severity{display:inline-block;font-size:.75rem;height:1rem;line-height:1rem;line-height:14px;max-width:54px;min-width:16px;overflow:hidden;padding-left:.125rem;padding-right:.125rem;position:relative;text-align:center;white-space:nowrap;--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.severity:before{background-color:currentColor;background-repeat:no-repeat;height:100%;left:0;position:absolute;top:0;width:100%;z-index:0;--tw-content:attr(data-severity);content:var(--tw-content);-webkit-mask:url('data:image/svg+xml;charset=utf-8,');mask:url('data:image/svg+xml;charset=utf-8,');-webkit-mask-size:100% 100%;mask-size:100% 100%}.severity:after,.severity:before{display:inline-block}.severity:after{--tw-scale-x:.75;--tw-scale-y:.75;content:attr(data-severity);line-height:20px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.severity[data-severity="1"]{--tw-text-opacity:1;color:rgb(185 28 28/var(--tw-text-opacity))}.severity[data-severity="2"]{--tw-text-opacity:1;color:rgb(249 115 22/var(--tw-text-opacity))}.severity[data-severity="3"]{--tw-text-opacity:1;color:rgb(250 174 26/var(--tw-text-opacity))}.severity[data-severity="4"]{--tw-text-opacity:1;color:rgb(184 150 100/var(--tw-text-opacity))}.severity[data-severity="5"]{--tw-text-opacity:1;color:rgb(158 163 176/var(--tw-text-opacity))}.severity-label{background-color:transparent}.severity-label:after,.severity-label:before{--tw-content:none;content:var(--tw-content)}.risk-high{color:rgb(220 38 38/var(--tw-text-opacity))}.risk-high,.risk-middle{--tw-text-opacity:1}.risk-middle{color:rgb(234 179 8/var(--tw-text-opacity))}.label.label-id{border-radius:var(--radius-full);flex:none;--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-300-rgb),var(--tw-ring-opacity));--label-bg:rgba(var(--color-canvas-rgb),.1)}.nav-feature{--nav-active-bg:var(--color-primary-100);--nav-active-color:var(--color-fore)}.nav-feature .nav-checkbox>.checkbox,.nav-feature .nav-checkbox>.checkbox-primary,.nav-feature .nav-item>a{align-items:center;border-radius:var(--radius);height:2rem;padding-left:.625rem;padding-right:.625rem}.nav-feature .nav-item>a>.icon{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.sortable-list .listitem{cursor:move;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-left:.5rem;padding-right:.5rem}.sortable-list .sortable-ghost>.listitem{--tw-bg-opacity:1;background-color:rgba(var(--color-warning-50-rgb),var(--tw-bg-opacity))}.sortable-empty-shadow{height:1px!important;left:0!important;opacity:0!important;pointer-events:none!important;position:absolute!important;top:0!important;width:1px!important}:root{--avatar-radius:12.5%;--avatar-bg:var(--color-surface)}.avatar{align-items:center;aspect-ratio:1/1;background:var(--avatar-bg);border-radius:var(--avatar-radius);display:inline-flex;justify-content:center;overflow:hidden;width:2rem}.avatar>img{height:100%;margin:0;-o-object-fit:cover;object-fit:cover;width:100%}.avatar.size-xs{width:1.25rem}.avatar.size-sm,.avatar.size-xs{font-size:.75rem;line-height:1rem}.avatar.size-sm{width:1.5rem}.avatar.size-lg{font-size:1.5rem;line-height:2rem;width:3rem}.avatar.size-xl{font-size:2.25rem;line-height:2.5rem;width:5rem}.avatar-group{display:flex;gap:.625rem}.avatar-group>.avatar{box-shadow:0 0 0 1px var(--color-canvas)}.avatar-group>*+*{margin-left:-1rem}.avatar-group.size-xs>*+*{margin-left:-.75rem}.avatar-group.size-sm>*+*{margin-left:-.875rem}.avatar-group.size-lg>*+*{margin-left:-1.25rem}.avatar-group.size-xl>*+*{margin-left:-1.5rem}.btn-group{display:flex;gap:1px}.btn-group>.btn.active{z-index:1}.btn-group>.btn:focus-within,.btn-group>.btn:hover{z-index:2}.btn-group>.btn.disabled,.btn-group>.btn:disabled{z-index:0}.btn-group>.btn:not(:first-child){border-bottom-left-radius:var(--radius-none);border-left-color:rgba(var(--color-canvas-rgb),.2);border-left-width:1px;border-top-left-radius:var(--radius-none)}.btn-group>.btn:not(:first-child):before{left:-1px}.btn-group>.btn:not(:last-child){border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none)}.color-picker-heading{align-items:center;font-weight:700;justify-content:space-between;margin-bottom:-.25rem;padding:.5rem}.color-picker-heading,.color-picker-row{display:flex;flex-direction:row}.color-picker-row{flex-wrap:wrap;gap:.5rem;padding:.75rem}.color-picker-item{align-items:center;border-radius:var(--radius-full);display:flex;height:1.25rem;justify-content:center;padding-left:.125rem;padding-right:.125rem;width:1.25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.pick-container{left:0;pointer-events:none;position:absolute;top:0;z-index:1600}.pick-pop{display:flex;flex-direction:column;opacity:0;pointer-events:auto;position:absolute;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);z-index:1200}.pick-pop.in{opacity:1}.date-picker-menu{--menu-bg:none}.date-picker-menu .mini-calendar{margin-top:-.75rem}.date-pick-menu-month,.date-pick-menu-years{display:flex;flex-direction:row;flex-wrap:wrap;gap:1px;max-height:237px;padding-bottom:.5rem;padding-left:.5rem;padding-right:.5rem}.date-pick-menu-years>.btn{width:2.5rem}.date-pick-menu-years>.btn.is-current{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.date-pick-menu-month>.btn.active,.date-pick-menu-years>.btn.active{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.date-pick-menu-month>.btn{width:3rem}.date-picker-menu-footer{border-top-width:1px;display:flex;flex-direction:row;padding:.25rem}.date-picker-menu-footer>.toolbar{flex:1 1 auto;justify-content:center}.date-picker-menu>.menu{border-right-width:1px}.date-picker-menu .menu-item{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.time-picker-menu{max-height:inherit}.time-picker-menu .menu-item>a{justify-content:center;padding-left:0;padding-right:0;text-align:center}.datetime-picker-menu{max-height:inherit}.mini-calendar{padding:.5rem}.mini-calendar>.row>.col{align-items:center;justify-content:center;width:14.2857%}.mini-calendar-day{height:2rem}.mini-calendar-day.disabled{pointer-events:none;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-200-rgb),var(--tw-bg-opacity));opacity:.5}.mini-calendar-day>.btn{width:2rem}.mini-calendar-day.is-weekend>.btn{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.mini-calendar-day.active>.btn,.mini-calendar-day.is-today>.btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.mini-calendar-day.selected>.btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.mini-calendar-day.is-out-month{opacity:.5}.i-time{border-color:currentColor;border-radius:50%;border-width:.08em;display:inline-block;height:1em;position:relative;width:1em}.i-time:after{border-color:currentColor;border-width:0 0 .08em .08em;height:.385em;left:.3846em;position:absolute;top:.08em;width:.385em;--tw-content:"";content:var(--tw-content)}.chevron-down,.chevron-left,.chevron-right,.chevron-up{align-items:center;display:inline-flex;height:1em;justify-content:center;position:relative;width:1em}.chevron-down:before,.chevron-left:before,.chevron-right:before,.chevron-up:before{display:block;height:.6923077em;transform-origin:center;width:.6923077em;--tw-translate-y:-0.125rem;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.chevron-left:before{--tw-translate-y:0px;--tw-translate-x:0.125rem;--tw-rotate:135deg}.chevron-left:before,.chevron-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-right:before{--tw-translate-y:0px;--tw-translate-x:-0.125rem;--tw-rotate:-45deg}.chevron-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.i-calendar{border-radius:2px;display:inline-block;height:.79em;margin-top:.16em;position:relative;width:1em}.i-calendar,.i-calendar:after,.i-calendar:before{border-color:currentColor;border-width:.08em}.i-calendar:after,.i-calendar:before{position:absolute;--tw-content:"";content:var(--tw-content)}.i-calendar:before{border-bottom-width:0;left:.15em;top:.307em;width:.6em}.i-calendar:after{border-bottom-width:0;border-top-width:0;height:.3077em;left:.17em;top:-.154em;width:.538em}:root{--modal-radius:var(--radius-lg);--modal-bg:rgba(var(--color-inverse-rgb),.4);--modal-sm:37.5rem;--modal-base:50rem;--modal-lg:75rem;--modal-xl:90rem}.modal{align-items:center;background-color:var(--modal-bg);bottom:0;display:none;justify-content:center;left:0;overflow:hidden;position:fixed;right:0;top:0;z-index:1500}.modal.load-indicator:before{background-color:transparent;transition-property:none}.modal.loading:after{--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.modal.loading .modal-dialog{opacity:0!important}.modal.show{display:flex}.modal-no-backdrop{background-color:transparent;pointer-events:none}.modal-hide{opacity:0!important}.modal-dialog{background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));pointer-events:auto;position:relative;--tw-bg-opacity:0.9;--tw-shadow:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--tw-shadow-colored:0 10px 50px -10px var(--tw-shadow-color),0 8px 20px -10px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);border-radius:var(--modal-radius);width:var(--modal-base)}.modal-content,.modal-dialog{max-height:100vh}.modal-content{display:flex;flex-direction:column;height:100%}.loading>.modal-dialog>.modal-content{opacity:0;visibility:hidden}.modal-dialog.loading{background-color:transparent}.modal-dialog.loading>.modal-content{display:none}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.modal-header{align-items:center;display:flex;flex:none;flex-wrap:nowrap;gap:1rem;padding:1rem 1.25rem;position:relative}.modal-title{flex:1 1 auto;font-size:1rem;font-weight:700;line-height:1.5rem}.modal-actions{position:absolute;right:.75rem;top:.75rem;z-index:15}.modal-body{flex:1 1 auto;overflow:auto;padding:1rem 1.25rem}.modal-footer{align-items:center;display:flex;flex:none;gap:.75rem;padding:1.25rem}.modal-dialog.size-full,.modal-dialog[data-size=full]{border-radius:var(--radius-none);height:100vh;width:100vw}.modal-dialog.size-sm,.modal-dialog[data-size=sm]{width:var(--modal-sm)}.modal-dialog.size-lg,.modal-dialog[data-size=lg]{width:var(--modal-lg)}.modal-dialog.size-xl,.modal-dialog[data-size=xl]{width:var(--modal-xl)}.modal-iframe{flex:1 1 auto;width:100%}.modal-trans{opacity:0;transition-duration:.2s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.modal-trans.in{opacity:1}.modal-trans>.modal-dialog{transition-property:transform,opacity;--tw-scale-x:.95;--tw-scale-y:.95;opacity:0;transition-duration:.3s}.modal-trans.in>.modal-dialog,.modal-trans>.modal-dialog{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.modal-trans.in>.modal-dialog{--tw-scale-x:1;--tw-scale-y:1;opacity:1}.modal-alert .modal-footer{justify-content:flex-end}.modal-alert .modal-header{margin-bottom:-1rem}.modal-alert .modal-body{overflow-wrap:break-word;white-space:pre-line}.modal-alert .modal-actions+.modal-body{padding-right:3rem}.modal-alert .modal-header+.modal-actions+.modal-body{padding-right:1.25rem}.file-selector{gap:.5rem;width:100%}.file-selector,.file-selector-box{display:flex;flex-direction:column}.file-selector-box{border-style:dashed;border-width:1px;gap:0;height:auto;justify-content:center;position:relative;--tw-border-opacity:1;background-color:rgba(var(--color-primary-50-rgb),.3);border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));padding:.5rem .75rem;--tw-ring-color:transparent;--state-color:rgba(var(--color-primary-500-rgb),.05)}.file-selector-box .text{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.is-dragging .file-selector-box{border-style:solid}.file-selector-btn{align-items:center;display:flex;gap:.5rem;position:relative}.is-dragging .file-selector-btn{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.file-selector-input{-webkit-appearance:none;-moz-appearance:none;appearance:none;bottom:0;cursor:pointer;left:0;opacity:.1;position:absolute;right:0;top:0}.file-selector-tip{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.file-selector.is-mode-button{flex-direction:column-reverse}.file-selector-list.is-empty{display:none}.file-selector-item .item-avatar{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.file-selector-item .item-subtitle{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.file-selector-item .item-content{flex:none;margin-right:.25rem;max-width:100%}.file-selector-item>.listitem:hover{background-color:rgba(var(--color-gray-500-rgb),.05)}.file-selector-item.is-renaming .item-avatar+.item-content{max-width:calc(100% - 32px)}.file-selector-rename-text{max-width:100%;min-width:100px;position:relative}.file-selector-rename-text>div{overflow:hidden;pointer-events:none;visibility:hidden;white-space:nowrap}.file-selector-rename-input{bottom:0;left:0;position:absolute;right:0;top:0}.file-selector-grid{align-items:flex-start;border-color:transparent;border-radius:var(--radius);border-width:1px;display:flex;flex-direction:row;flex-wrap:wrap;gap:var(--file-selector-grid-gap);--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity));padding:.5rem}.file-selector-grid-item{height:var(--file-selector-grid-height)}.file-selector-grid-btn,.file-selector-grid-item{width:var(--file-selector-grid-width)}.file-selector-grid-btn{aspect-ratio:1/1;border-style:dashed;border-width:1px;display:flex;flex-direction:column;gap:0;height:auto;justify-content:center;--tw-border-opacity:1;background-color:rgba(var(--color-primary-50-rgb),.3);border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));padding:.5rem;--tw-ring-color:transparent;--state-color:rgba(var(--color-primary-500-rgb),.05)}.file-selector-grid-btn .text{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.file-selector-grid-item .listitem{flex-direction:column;height:100%;padding:0;position:relative;width:100%}.file-selector-grid-item .item-avatar{border-radius:var(--radius);border-width:1px;width:100%;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.file-selector-grid-item .item-avatar.has-icon>.icon{font-size:calc(var(--file-selector-grid-width)/2)}.file-selector-grid-item .item-content,.file-selector-grid-item .toolbar{aspect-ratio:1/1;left:0;position:absolute;right:0;top:0;width:100%}.file-selector-grid-item .item-title{bottom:-1.25rem;font-size:.75rem;left:0;line-height:1rem;overflow:hidden;position:absolute;right:1.5rem;white-space:nowrap}.file-selector-grid-item .item-subtitle{border-radius:var(--radius-full);bottom:.25rem;left:.25rem;position:absolute;--tw-bg-opacity:1;background-color:rgba(var(--color-fore-rgb),var(--tw-bg-opacity));font-size:.75rem;line-height:1rem;padding-left:.25rem;padding-right:.25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.file-selector-grid-item:hover .item-subtitle{opacity:1}.file-selector-grid-item .toolbar .btn[data-remove-file]{background-color:rgba(var(--color-inverse-rgb),.5);padding:.375rem;position:absolute;right:1px;top:1px;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.file-selector-grid-item .toolbar .btn[data-rename-file]{bottom:-1.5rem;padding:0;position:absolute;right:0}.file-selector-grid .file-selector-rename{bottom:0;height:1.5rem;position:absolute;top:auto}.file-selector-grid .file-selector-rename-text{width:100%}.is-dragging .file-selector-grid{border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-primary-400-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}:root{--nav-radius:var(--radius);--nav-active-color:var(--color-primary-500);--nav-active-bg:var(--color-inherit);--nav-heading-color:var(--color-gray-500);--nav-gap:0.25rem;--nav-item-color:inherit;--nav-item-bg:transparent;--nav-item-padding:1rem;--nav-item-height:2rem;--nav-item-gap:0.75rem;--nav-divider-height:calc(var(--nav-item-height)/2);--nav-divider-margin:0.5rem}.nav{list-style-type:none;padding-left:0}.nav,.nav-item{align-items:center;display:flex;position:relative}.nav-item{gap:var(--nav-item-gap)}.nav-item>a{align-items:center;background-color:var(--nav-item-bg);color:var(--nav-item-color);cursor:pointer;display:flex;gap:var(--nav-gap);height:var(--nav-item-height);justify-content:center;padding-left:var(--nav-item-padding);padding-right:var(--nav-item-padding)}.nav-item>a>.text{white-space:nowrap}.nav-item>.active{font-weight:700;--nav-item-color:var(--nav-active-color);--nav-item-bg:var(--nav-active-bg)}.nav-item>.selected{--nav-item-color:var(--nav-selected-color);--nav-item-bg:var(--nav-selected-bg)}.nav-item>.disabled{--nav-item-color:var(--nav-disabled-color);--nav-item-bg:var(--nav-disabled-bg)}.nav-item>.disabled>*{opacity:var(--opacity-disabled)}.nav-divider,.nav>.divider{align-self:center;height:var(--nav-divider-height);margin-left:var(--nav-divider-margin);margin-right:var(--nav-divider-margin)}.nav-heading{align-items:center;color:var(--nav-heading-color);display:flex;font-weight:700;gap:.25rem;height:2rem;justify-content:center;padding-left:1rem;padding-right:1rem}.nav-space{flex:1 1 auto;width:1rem}.nav-compact{--nav-gap:0.25rem;--nav-item-gap:0.5rem;--nav-item-height:1.75rem;--nav-item-padding:0.5rem;--nav-divider-margin:0.25rem}.nav-primary>.nav-item{position:relative}.nav-primary>.nav-item:hover{z-index:10}.nav-primary>.nav-item+.nav-item{margin-left:-1px}.nav-primary>.nav-item>a{border-radius:var(--radius-none);border-width:1px}.nav-primary>.nav-item:first-child>a,.nav-primary>.nav-item:has(.nav-heading)+.nav-item>a{border-bottom-left-radius:var(--nav-radius);border-top-left-radius:var(--nav-radius)}.nav-primary>.nav-item:last-child>a{border-bottom-right-radius:var(--nav-radius);border-top-right-radius:var(--nav-radius)}.nav-primary>.nav-item>.active{--tw-text-opacity:1;background:var(--nav-active-color);border-color:var(--nav-active-color);color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.nav-primary>.nav-divider{display:none}.nav-secondary>.nav-item>a{border-radius:var(--radius-none);position:relative}.nav-secondary>.nav-item>a:after{bottom:-2px;display:block;height:2px;left:0;position:absolute;right:0;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));--tw-content:"";content:var(--tw-content)}.nav-secondary>.nav-item>.active:after{background-color:currentColor}.nav-secondary>.nav-divider{margin:0 0 0 -1px}.nav-tabs>.nav-item>a{border-bottom-left-radius:var(--radius-none);border-bottom-right-radius:var(--radius-none);position:relative}.nav-tabs>.nav-item>a:after{border-color:transparent;border-width:1px;bottom:-1px;display:block;left:-1px;pointer-events:none;position:absolute;right:-1px;top:-1px;--tw-border-opacity:1;border-bottom-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-content:"";border-top-left-radius:inherit;border-top-right-radius:inherit;content:var(--tw-content)}.nav-tabs>.nav-item>.active:after{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-bottom-color:transparent}.nav-tabs>.nav-divider{margin:0 0 0 -1px}.nav-pills>.nav-item>a{border-radius:var(--radius-full)}.nav-pills>.nav-item>.active{--tw-text-opacity:1;background:var(--nav-active-color);border-color:var(--nav-active-color);color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.nav-steps{--nav-item-bg:var(--color-canvas);--nav-active-bg:var(--color-primary-500);--nav-active-color:var(--color-canvas);--nav-selected-bg:var(--color-secondary-500);--nav-selected-color:var(--color-canvas)}.nav-steps>.nav-item+.nav-item>a{padding-left:calc(var(--nav-item-padding) + var(--nav-item-height)/3)}.nav-steps>.nav-item>a:after,.nav-steps>.nav-item>a:before{border-style:solid;height:0;left:100%;position:absolute;width:0;z-index:2;--tw-content:"";border-color:transparent;border-left-color:var(--nav-item-bg,var(--color-canvas));border-width:calc(var(--nav-item-height)/2);border-left-width:calc(var(--nav-item-height)/3);border-right-width:0;content:var(--tw-content)}.nav-steps>.nav-item>a:before{background-color:transparent!important;border-left-color:var(--color-border);bottom:auto;left:calc(100% + 5.5px);opacity:1!important;right:auto;top:.4rem;transform:none;z-index:1;--nav-item-height:1.2rem}.nav-steps>.nav-item:has(+.nav-item>.active)>.selected:before,.nav-steps>.nav-item:has(+.nav-item>.active,+.nav-item>.selected)>a:not(.active,.selected):before,.nav-steps>.nav-item:has(+.nav-item>.selected)>.active:before,.nav-steps>.nav-item:last-child>a:after,.nav-steps>.nav-item:last-child>a:before{display:none}.nav-steps>.nav-item>a:hover{--nav-item-bg:var(--color-gray-100)}.nav-steps>.nav-item>.active:hover{--nav-item-bg:var(--color-primary-600)}.nav-steps>.nav-item>.selected:hover{--nav-item-bg:var(--color-secondary-600)}.nav-stacked{flex-direction:column}.nav-stacked>.nav-item{width:100%}.nav-stacked>.nav-heading,.nav-stacked>.nav-item>a{justify-content:flex-start;width:100%}.nav-stacked>.nav-divider{height:1px;margin:.5rem 0;width:100%}.nav-primary.nav-stacked>.nav-item>a{height:2.5rem}.nav-primary.nav-stacked>.nav-item+.nav-item{margin-left:0;margin-top:-1px}.nav-primary.nav-stacked>.nav-item:first-child>a{border-bottom-left-radius:0;border-top-left-radius:var(--nav-radius);border-top-right-radius:var(--nav-radius)}.nav-primary.nav-stacked>.nav-item:last-child>a{border-bottom-left-radius:var(--nav-radius);border-bottom-right-radius:var(--nav-radius);border-top-right-radius:0}.nav-secondary.nav-stacked>.nav-item>a:after{bottom:0;height:100%;left:auto;right:0;top:0;width:2px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity))}.nav-secondary.nav-stacked>.nav-item>.active:after{background-color:currentColor}.nav-secondary.nav-stacked>.nav-divider{margin:0}.nav-tabs.nav-stacked>.nav-item>a{border-bottom-left-radius:var(--nav-radius);border-bottom-right-radius:var(--radius-none);border-top-right-radius:var(--radius-none);position:relative}.nav-tabs.nav-stacked>.nav-item>a:after{--tw-border-opacity:1;border-bottom-color:transparent;border-bottom-left-radius:inherit;border-right-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-top-left-radius:inherit}.nav-tabs.nav-stacked>.nav-item>a.active:after{--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));border-right-color:transparent}.nav-tabs.nav-stacked>.nav-divider{margin:0}.nav-pills.nav-stacked>.nav-item+.nav-item{margin-top:.25rem}.nav-justified>.nav-item:not(.flex-none,.nav-divider){flex:1 1 auto}.nav-justified>.nav-item>a{width:100%}.arrow,.arrow:before{background:inherit;height:calc(var(--arrow-size)*1.4142);position:absolute;width:calc(var(--arrow-size)*1.4142)}.arrow{visibility:hidden;--arrow-size:5px}.arrow:before{border:inherit;content:"";visibility:visible;--tw-rotate:45deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.arrow-top,.arrow-up{border-bottom:inherit;border-right:inherit;border-width:1px 0 0 1px;top:calc(1px - var(--arrow-size))}.white>.arrow-top,.white>.arrow-up{top:calc(0px - var(--arrow-size))}.arrow-bottom,.arrow-down{border-left:inherit;border-top:inherit;border-width:0 1px 1px 0;bottom:calc(1px - var(--arrow-size))}.white>.arrow-bottom,.white>.arrow-down{bottom:calc(0px - var(--arrow-size))}.arrow-left{border-right:inherit;border-top:inherit;border-width:0 0 1px 1px;left:calc(1px - var(--arrow-size))}.white>.arrow-left{left:calc(0px - var(--arrow-size))}.arrow-right{border-bottom:inherit;border-left:inherit;border-width:1px 1px 0 0;right:calc(1px - var(--arrow-size))}.white>.arrow-right{right:calc(0px - var(--arrow-size))}.popover{display:none;left:0;position:absolute;top:0;width:-moz-max-content;width:max-content}.popover.show{display:block}.popover-heading{align-items:center;border-top-left-radius:inherit;border-top-right-radius:inherit;display:flex;gap:1rem;height:2.5rem;justify-content:space-between;position:relative;z-index:1;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:.75rem;padding-right:.5rem}.popover-title{flex:1 1 auto;font-weight:700}.popover-content{padding:.75rem;position:relative;z-index:1}.popover-arrow{z-index:0}.has-heading>.popover-arrow.arrow-top,.has-heading>.popover-arrow.arrow-up{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.popover>.btn-close{position:absolute;right:.5rem;top:.625rem;z-index:2}.btn-close+.popover-content{padding-right:3rem}.btn.with-popover-show{--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.with-popover-show[data-pop-placement=top]>.caret{--tw-rotate:180deg}.with-popover-show[data-pop-placement=left]>.caret,.with-popover-show[data-pop-placement=top]>.caret{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.with-popover-show[data-pop-placement=left]>.caret{--tw-rotate:90deg}.with-popover-show[data-pop-placement=right]>.caret{--tw-rotate:-90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.pager{align-items:center;display:flex;gap:.25rem;white-space:nowrap}.menu.pager-size-menu{display:grid!important;grid-template-columns:repeat(3,minmax(0,1fr));text-align:center}.menu.pager-size-menu>.menu-item>a{margin:.125rem}.pager .pager-goto-group>.form-control{width:3rem}.pager .pager-goto-group>.input-group-addon{border-width:1px;--tw-border-opacity:1;border-color:rgba(var(--color-gray-300-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.pager>.pager-nav.active{--tw-text-opacity:1;box-shadow:0 0 0 1px var(--color-primary-500);color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.panel{border-radius:var(--radius);overflow:hidden;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05}.panel-heading{background-color:var(--panel-heading-bg);flex-wrap:nowrap;gap:1rem;justify-content:space-between;padding:.5rem 1rem}.panel-heading,.panel-title{align-items:center;display:flex}.panel-title{font-weight:700;gap:.5rem;margin:0}.panel-actions{align-items:center;display:flex;margin-right:-.5rem}.panel-body{padding:.75rem 1rem}.panel-footer{align-items:center;background-color:var(--panel-footer-bg);display:flex;gap:.5rem;padding:.5rem 1rem}.size-sm .panel-body,.size-sm .panel-footer,.size-sm .panel-heading{padding:.375rem .75rem}.size-lg .panel-body,.size-lg .panel-footer,.size-lg .panel-heading{padding:1rem 1.25rem}.picker{position:relative}.picker-select{align-items:center;gap:.25rem;justify-content:space-between}.picker-select,.picker-select.form-control{display:flex}.picker-select-placeholder{flex:1 1 auto;--tw-text-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-text-opacity))}.picker-select-multi .picker-select-placeholder{padding-left:.25rem;padding-right:.25rem}.picker-single-selection{flex:1 1 auto;min-width:0;overflow:hidden;white-space:nowrap}.picker-deselect-btn{border-radius:var(--radius-full);padding:.25rem}.picker-deselect-btn:not(:hover){opacity:.7}.picker-select-multi.form-control{height:auto;min-height:32px;padding-left:.25rem}.picker-multi-selections{display:flex;flex-wrap:wrap;gap:.25rem;min-width:0}.picker-multi-selection{align-items:center;border-radius:var(--radius-full);border-width:1px;display:flex;max-width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:.5rem}.readonly .picker-multi-selection{padding-right:.5rem}.picker-multi-selection>.text{max-width:180px;min-width:0;overflow:clip;white-space:nowrap}.picker-no-search{cursor:default}.picker-menu-list{border-style:none;flex:1 1 auto;min-height:0;overflow-y:auto;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.picker-menu-search+.picker-menu-list.menu{margin-top:-.125rem;padding-top:0}.picker-menu-list.tree{padding:.5rem}.picker-menu-list .tree-item>.selected .item-content{font-weight:400}.picker-menu .search-menu-footer{border-top-width:1px;padding-bottom:.25rem;padding-top:.25rem}.picker-search-input{border-color:transparent;height:1.75rem;outline-width:0!important;padding-left:0;padding-right:2rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color)!important;--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)!important;box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)!important}.picker-search{flex:none;position:relative;width:100%}.picker-search>.magnifier{opacity:.5;position:absolute;right:0;top:.5rem}.picker-search-clear.btn{cursor:pointer;height:1.25rem;position:absolute;right:0;top:.25rem;width:1.25rem}.picker-search.is-inline{min-width:64px;width:4rem}.is-inline>.picker-search-input{height:1.25rem;min-width:64px;padding-left:.25rem;padding-right:.25rem}.picker-search-measure{height:0;left:0;overflow:hidden;position:absolute;top:0;white-space:nowrap}.split{display:flex;flex-direction:row}.split-vert{flex-direction:column}.split-cell{min-height:0;min-width:0}.has-animation>.split-cell{transition-duration:.15s;transition-property:width,height;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter{align-items:stretch;border-radius:var(--radius);cursor:col-resize;display:flex;flex:none;flex-direction:row;justify-content:center;position:relative}.gutter-vert{cursor:row-resize;flex-direction:column}.gutter:before{display:block;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:"";content:var(--tw-content)}.gutter-horz:before{width:1px}.gutter-vert:before{height:1px}.gutter-horz:hover:before{width:75%}.gutter-vert:hover:before{height:75%}.gutter-resize-handler,.gutter-toggle{align-items:center;border-radius:var(--radius-lg);border-width:1px;display:flex;height:1.75rem;justify-content:center;margin-top:-.875rem;position:absolute;top:50%;width:.75rem;--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity));transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter-toggle>span{--tw-scale-x:.75;--tw-scale-y:.75;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.gutter:hover .gutter-toggle{--tw-border-opacity:1;border-color:rgba(var(--color-gray-500-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.gutter .gutter-toggle:hover{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.is-last>.gutter-toggle{--tw-scale-x:-1}.is-first>.gutter-toggle,.is-last>.gutter-toggle{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.is-first>.gutter-toggle{--tw-scale-x:1}.gutter-vert .gutter-toggle{left:50%;margin-left:-.375rem;margin-top:0;top:auto;--tw-rotate:90deg}.gutter-vert .gutter-toggle,.gutter.is-next-collapsed>.gutter-toggle{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.gutter.is-next-collapsed>.gutter-toggle{--tw-scale-x:1}.gutter.is-prev-collapsed>.gutter-toggle{--tw-scale-x:-1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.gutter-horz.is-first.is-prev-collapsed{transform:translateX(calc(-1px - var(--split-gutter-size)/2))}.gutter-horz.is-last.is-next-collapsed{transform:translateX(calc(1px + var(--split-gutter-size)/2))}.gutter-vert.is-first.is-prev-collapsed{transform:translateY(calc(-1px - var(--split-gutter-size)/2))}.gutter-vert.is-last.is-next-collapsed{transform:translateY(calc(1px + var(--split-gutter-size)/2))}.gutter-resize-handler{background-color:transparent;border-width:0}.gutter-resize-handler:before{border-left-width:1px;border-right-width:1px;bottom:0;left:.25rem;position:absolute;right:.25rem;top:0;--tw-content:"";content:var(--tw-content)}.sidebar{flex:none!important;position:relative;--gutter-width:1px;--sidebar-duration:200ms}.has-sidebar-animation .sidebar{transition-duration:.15s;transition-duration:var(--sidebar-duration);transition-property:width,margin;transition-timing-function:cubic-bezier(.4,0,.2,1)}.sidebar-left.is-collapsed{margin-left:calc(var(--gutter-width)*-1)}.sidebar-right.is-collapsed{margin-right:calc(var(--gutter-width)*-1)}.sidebar.is-collapsed>*,.sidebar.is-expanded.is-animating>*{display:none}.sidebar.is-collapsed>.sidebar-gutter{display:flex!important}.sidebar-gutter{bottom:0;left:100%;position:absolute;top:0;width:var(--gutter-width)}.sidebar-right>.sidebar-gutter{left:auto;right:100%}.is-collapsed>.gutter>.gutter-toggle>span{--tw-rotate:-180deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.sidebar-gutter:before{border-radius:var(--radius-full);opacity:0}.sidebar-gutter:hover:before{opacity:1;width:.5rem}.is-expanded .sidebar-gutter.gutter-border:before{opacity:1}.is-sidebar-resizing{cursor:col-resize}:root{--table-head-bg:var(--color-surface);--table-striped-color:var(--color-gray-50);--table-hover-color:rgba(var(--color-primary-500-rgb),.05);--table-border-color:var(--color-border)}.table{border-color:var(--table-border-color);width:100%}.table>thead{background-color:var(--table-head-bg)}.table>*>tr{border-bottom-width:1px}.table>*>tr>*{padding:.5rem 1rem}.table-striped>tbody>tr:nth-child(2n){background:var(--table-striped-color)}.table-hover>tbody>tr:hover>*{background:var(--table-hover-color)}.table.bordered>*>tr>*{border-width:1px}.table.borderless>*>tr,.table.borderless>*>tr>*{border-style:none}.condensed>*>tr>*{padding:.375rem .75rem}.table-fixed{table-layout:fixed}.table-fixed>*>tr>*{overflow:hidden;white-space:nowrap}.toolbar{align-items:center;display:flex;position:relative}.toolbar>.divider{margin:.5rem;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity))}.toolbar-space{flex:1 1 auto;height:1px;width:1px}.toolbar>.dropdown.show{align-items:center;display:flex;position:relative}:root{--tooltip-bg:var(--skin-color,var(--color-inverse));--tooltip-text:var(--skin-text,var(--color-canvas));--tooltip-arrow:6px;--tooltip-delay:0.5s}.hint,[class*=" hint-"],[class^=hint-]{position:relative}.hint:before,[class*=" hint-"]:before,[class^=hint-]:before{border-style:solid;height:0;position:absolute;width:0;--tw-content:"";border-color:var(--tooltip-bg) transparent transparent transparent;border-width:var(--tooltip-arrow) var(--tooltip-arrow) 0 var(--tooltip-arrow);content:var(--tw-content);margin-bottom:calc(0px - var(--tooltip-arrow))}.hint:after,[class*=" hint-"]:after,[class^=hint-]:after{background-color:var(--tooltip-bg);border-color:var(--tooltip-color);border-radius:var(--radius);color:var(--tooltip-text);font-size:.75rem;line-height:1rem;max-width:28rem;overflow:hidden;padding:.25rem .5rem;position:absolute;white-space:nowrap;--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-content:attr(data-hint);content:var(--tw-content);text-shadow:0 1px 0 var(--tooltip-bg)}.hint:after,.hint:before,[class*=" hint-"]:after,[class*=" hint-"]:before,[class^=hint-]:after,[class^=hint-]:before{bottom:100%;left:50%;opacity:0;pointer-events:none;transition-delay:0s;transition-duration:.15s;transition-property:opacity,visibility;transition-timing-function:cubic-bezier(.4,0,.2,1);transition-timing-function:cubic-bezier(.4,0,1,1);visibility:hidden;z-index:1800;--tw-translate-x:-50%;--tw-translate-y:calc(var(--tooltip-arrow)*-1);transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint:hover:after,.hint:hover:before,[class*=" hint-"]:hover:after,[class*=" hint-"]:hover:before,[class^=hint-]:hover:after,[class^=hint-]:hover:before{opacity:1;transition-delay:var(--tooltip-delay);visibility:visible}.hint-bottom:before{border-color:transparent transparent var(--tooltip-bg) transparent;border-width:0 var(--tooltip-arrow) var(--tooltip-arrow) var(--tooltip-arrow);margin-bottom:auto;margin-top:calc(0px - var(--tooltip-arrow))}.hint-bottom:after,.hint-bottom:before{bottom:auto;top:100%;--tw-translate-y:var(--tooltip-arrow);transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-left:before{border-color:transparent transparent transparent var(--tooltip-bg);border-width:var(--tooltip-arrow) 0 var(--tooltip-arrow) var(--tooltip-arrow);margin-bottom:auto;margin-right:calc(0px - var(--tooltip-arrow))}.hint-left:after,.hint-left:before{bottom:50%;left:auto;right:100%;--tw-translate-x:calc(var(--tooltip-arrow)*-1);--tw-translate-y:50%;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-right:before{border-color:transparent var(--tooltip-bg) transparent;border-width:var(--tooltip-arrow) var(--tooltip-arrow) var(--tooltip-arrow) 0;margin-bottom:auto;margin-left:calc(0px - var(--tooltip-arrow))}.hint-right:after,.hint-right:before{bottom:50%;left:100%;--tw-translate-x:var(--tooltip-arrow);--tw-translate-y:50%;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.hint-lg:after,.hint-sm
+.hint-md:after:after,.hint-xl:after{white-space:normal;word-break:break-all}.hint-sm:after{width:4rem}.hint-md:after{width:8rem}.hint-lg:after{width:16rem}.hint-xl:after{width:24rem}.hint-primary{--tooltip-bg:var(--color-primary-500)}.hint-success{--tooltip-bg:var(--color-success-500)}.hint-danger{--tooltip-bg:var(--color-danger-500)}.hint-warning{--tooltip-bg:var(--color-warning-500)}.hint-important{--tooltip-bg:var(--color-important-500)}.hint-special{--tooltip-bg:var(--color-special-500)}.tooltip{background-color:var(--tooltip-bg);border-color:var(--tooltip-color);border-radius:var(--radius);color:var(--tooltip-text);font-size:.75rem;line-height:1rem;max-width:28rem;padding:.25rem .5rem;z-index:1800}.tooltip:not(.white)>.arrow{border-width:0}.tooltip.white>.arrow{border-color:inherit}.tooltip-has-title{--tw-bg-opacity:0.8;padding:.5rem .75rem .75rem;--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.tooltip-has-title>.arrow{opacity:.75}.tooltip-heading{align-items:center;display:flex;font-size:.8125rem;font-weight:700;gap:1rem;justify-content:space-between;line-height:1.25rem;padding:.25rem}.tooltip-heading>.btn-close{margin-right:-.25rem}.tooltip-content{padding:.25rem}.tree-item-inner{flex-direction:row;min-height:24px;padding-left:var(--list-nested-indent)}.tree-item-inner,.tree-toggle{align-items:center;display:flex}.tree-toggle{border-radius:var(--radius);flex:none;height:1rem;justify-content:center;margin-right:-.375rem;width:1rem;--caret-size:5px;--caret-opacity:.3}.tree-item-inner>.item-icon{opacity:.5;width:1rem}.tree-item-inner:hover>.item-icon{opacity:.8}.tree-item-inner.has-hover{border-radius:var(--radius)}.tree-item-inner .item-title:not(:hover),.tree-item-inner>a.item-title:not(:hover){color:inherit}.tree-item-inner>.toolbar{margin-left:1rem;opacity:.6}.tree-item-inner:hover>.toolbar{opacity:1}.tree-item>.active{background:var(--menu-active-bg);color:var(--menu-active-color)}.tree-item>.selected{background:var(--menu-selected-bg)}.tree-item>.selected .item-content{color:var(--menu-selected-color);font-weight:700}.tree.search-menu-on-top>.search-box{left:0;right:0}.tree-lines .tree{position:relative}.tree-lines .tree-item{--tree-line-indent:calc(var(--list-nested-indent) + 8px)}.tree-lines .tree:before{border-left-width:1px;bottom:.5rem;display:block;left:var(--tree-line-indent);position:absolute;top:-.5rem;--tw-content:"";content:var(--tw-content)}.upload .upload-tip{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.upload .draggable-area{background-color:rgba(var(--color-primary-50-rgb),.2);border:1px dashed var(--color-primary-300)}.upload .draggable-area.dragover{background-color:rgba(var(--color-primary-500-rgb),.1);border-style:solid}.upload .upload-tip{color:var(--color-slate-500)}.file-item>.img{height:120px;width:120px}.upload .file-item:hover .file-size{display:flex!important}.form-batch-container{overflow-y:auto}.form-batch-table{min-width:100%;table-layout:fixed;--table-head-bg:var(--color-canvas)}.form-batch-table>*>tr{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.form-batch-table>*>tr>*{padding-left:.375rem;padding-right:.375rem;vertical-align:top}.form-batch-table>*>tr>th{text-align:left;vertical-align:middle}.form-batch-head[data-name=ACTIONS]{width:5rem}.form-batch-head[data-name=ACTIONS][data-action-count="3"]{width:6rem}.form-batch-label{display:inline}.form-batch-control>textarea.form-control{height:2rem}.form-batch-btn+.btn{margin-left:.25rem}.form-batch-table>tbody[data-count="1"] .form-batch-btn[data-type=delete]{display:none}.form-batch-ditto{position:relative}.form-batch-ditto-btn{bottom:0;height:auto;opacity:.5;padding-left:.5rem;padding-right:.5rem;position:absolute!important;right:0;top:0}.form-batch-ditto-btn:after{bottom:.5rem;left:-1px;position:absolute;top:.5rem;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-border-rgb),var(--tw-bg-opacity));--tw-content:"";content:var(--tw-content)}[data-ditto=on] .form-batch-ditto-btn{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity));opacity:1}.form-batch-row-actions{padding-bottom:.75rem!important;padding-top:.75rem!important}.form-batch-ditto-wrapper{position:relative}.form-batch-ditto-control .form-control{padding-right:calc(var(--form-batch-ditto-width) + 8px)}.form-batch-ditto-control .input-control>.input-control-suffix{right:var(--form-batch-ditto-width)}.form-batch-ditto-control .input-control>.form-control{padding-right:calc(var(--form-batch-ditto-width) + var(--input-control-suffix))}.form-batch-ditto-control .pick-pri{padding-right:calc(var(--form-batch-ditto-width) + 8px)}.datalist{--datalist-label-width:68px}.datalist-item{display:flex;gap:.5rem;padding-bottom:.375rem;padding-top:.375rem}.datalist-item-label{align-items:center;display:flex;flex:none;justify-content:flex-end;overflow:hidden;white-space:nowrap;width:var(--datalist-label-width);--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.datalist-item-content{align-items:center;display:flex;flex:1 1 0%;gap:.5rem}.dropmenu-btn{gap:.25rem;padding-left:.5rem;padding-right:.5rem}.dropmenu-btn>.text{max-width:180px;overflow:hidden}.dropmenu-btn>.is-leading{left:-.625rem;opacity:.6;position:absolute}.dropmenu-btn>.is-caret{align-items:center;background-color:rgba(var(--color-canvas-rgb),.2);border-radius:var(--radius);display:flex;height:1rem;justify-content:center;width:1rem}.dropmenu-nav{border-bottom-width:1px;margin-left:.75rem;margin-right:.75rem;margin-top:.25rem}.has-search .dropmenu-nav{margin-top:-.5rem}.dropmenu-nav>.nav-secondary{gap:.5rem}.dropmenu-nav>.nav-secondary>.nav-item>a{border-radius:var(--radius);padding-left:.5rem;padding-right:.5rem}.dropmenu-nav>.nav-secondary>.nav-item>a:after{bottom:-1px;left:1rem;opacity:0;right:1rem}.dropmenu-nav>.nav-secondary>.nav-item>.active:after{left:.5rem;opacity:1;right:.5rem;transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dropmenu-title{font-size:.75rem;font-weight:700;line-height:1rem;margin-bottom:-.5rem;padding:.75rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.dropmenu-list{min-height:0;overflow-x:hidden;overflow-y:auto;padding:.5rem .75rem}.dropmenu.loading>*{opacity:0}.dropmenu-item .tree-item-inner{border-radius:var(--radius);cursor:pointer;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dropmenu-item.is-item.active>.tree-item-inner{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.tree-item-inner.is-link:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.tree-item-inner.is-link:hover .item-content,.tree-item-inner.is-link:hover .item-trailing-icon,.tree-item-inner.is-link:hover .label{color:inherit}.tree-item-inner.is-toggle:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity))}.dropmenu-item+.tree-item{margin-top:.125rem}.dropmenu-item .is-match{font-weight:700;text-decoration-line:underline}.dropmenu-item .item-title,.dropmenu-item .label{overflow:hidden;white-space:nowrap}.dropmenu-item .item-content{padding-left:.375rem;padding-right:.375rem}.dropmenu-item *+.item-content{padding-left:0}.tree-item-inner.is-toggle .item-title{opacity:.6}.tree-item-inner.is-toggle:hover .item-title{opacity:1}.dropmenu-item-check{align-items:center;display:flex;flex:1 1 auto;justify-content:flex-end;padding-right:.5rem}.dropmenu-item .nested-toggle-icon.is-empty{width:.25rem}.dropmenu-item .item-icon{margin-right:-.25rem}.card-list{--list-gap:.625rem;--list-count-per-row:1}.card-list,.card-list-item{padding:calc(var(--list-gap)/2)}.card-list-item{width:calc(100%/var(--list-count-per-row))}.card-grid{display:flex;flex-wrap:wrap}.card-grid .card{height:100%}:root{--form-control-border:var(--color-border-strong)}.checkbox-primary.disabled,.checkbox-primary.disabled>label,.checkbox-primary>input[type=checkbox]:disabled,.checkbox-primary>input[type=checkbox]:disabled+label,.radio-primary.disabled,.radio-primary.disabled>label,.radio-primary>input[type=radio],.radio-primary>input[type=radio]:disabled+label{filter:none!important}.checkbox-primary.disabled>label,.radio-primary.disabled>label{opacity:1}.form-actions{gap:1rem;justify-content:center}.form-actions .btn{min-width:96px}.form-control-static{min-height:32px;padding-bottom:.375rem;padding-top:.375rem}:root{--zt-panel-form-max-width:1000px}.size-sm{--zt-panel-form-max-width:800px}.size-lg{--zt-panel-form-max-width:1200px}.panel-body>.container,.panel-heading>.container{max-width:var(--panel-container-width);min-width:0;padding-left:var(--panel-container-padding);padding-right:var(--panel-container-padding)}.panel-heading>.container{align-items:center;display:flex;flex-direction:row;flex-wrap:nowrap;gap:1rem;justify-content:space-between;min-height:48px}.panel-form{border-radius:var(--radius-md);margin-bottom:1rem;margin-left:auto;margin-right:auto;max-width:var(--zt-panel-form-max-width);min-width:var(--zt-panel-form-min-width);overflow:visible;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-bottom:1rem;padding-left:1rem;padding-right:1rem;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.panel-form .form-actions{background-color:rgba(var(--color-canvas-rgb),.8);bottom:0;padding-bottom:1rem;padding-top:1rem;position:sticky;z-index:3;--tw-backdrop-blur:blur(8px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.panel-form .form-grid{margin-left:calc(0px - var(--form-grid-gap-y-half));margin-right:calc(0px - var(--form-grid-gap-y-half));padding-bottom:0}.panel-form-toolbar{padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half);width:100%}.panel-form-toolbar>.toolbar{gap:1rem;padding-bottom:.75rem;padding-top:.75rem}.panel-form-divider{margin-bottom:.75rem;margin-top:1rem;padding-left:var(--form-grid-gap-x-half);padding-right:var(--form-grid-gap-x-half);width:100%}.panel-form-divider:before{background-color:rgba(var(--color-border-rgb),.7);display:block;height:1px;--tw-content:"";content:var(--tw-content)}.is-full .btn-full-form,.is-lite .btn-lite-form{z-index:1;--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-300-rgb),var(--tw-ring-opacity))}.btn-toggle-fold:after{content:attr(data-expand-text)}.show-fold-items .btn-toggle-fold:after{content:attr(data-collapse-text)}.is-foldable,.is-full .full\:hidden,.is-full .lite\:visible,.is-full .panel-form-divider,.is-full .panel-form-toolbar,.is-lite .full\:visible,.is-lite .lite\:hidden,.no-foldable-items .btn-toggle-fold{display:none}.is-foldable.is-pinned,.is-full .full\:visible,.is-full .is-foldable,.is-full .lite\:hidden,.is-lite .full\:hidden,.is-lite .lite\:visible,.show-fold-items .is-foldable{display:block}.is-full .full\:w-1\/2,.is-lite .lite\:w-1\/2{width:50%}.is-full .full\:w-1\/3,.is-lite .lite\:w-1\/3{width:33.333333%}.is-full .full\:w-2\/3,.is-lite .lite\:w-2\/3{width:66.666667%}.is-full .full\:w-1\/4,.is-lite .lite\:w-1\/4{width:25%}.is-full .full\:w-2\/4,.is-lite .lite\:w-2\/4{width:50%}.is-full .full\:w-3\/4,.is-lite .lite\:w-3\/4{width:75%}.is-full .full\:w-1\/5,.is-lite .lite\:w-1\/5{width:20%}.is-full .full\:w-2\/5,.is-lite .lite\:w-2\/5{width:40%}.is-full .full\:w-3\/5,.is-lite .lite\:w-3\/5{width:60%}.is-full .full\:w-4\/5,.is-lite .lite\:w-4\/5{width:80%}.is-full .full\:w-1\/6,.is-lite .lite\:w-1\/6{width:16.666667%}.is-full .full\:w-2\/6,.is-lite .lite\:w-2\/6{width:33.333333%}.is-full .full\:w-3\/6,.is-lite .lite\:w-3\/6{width:50%}.is-full .full\:w-4\/6,.is-lite .lite\:w-4\/6{width:66.666667%}.is-full .full\:w-5\/6,.is-lite .lite\:w-5\/6{width:83.333333%}.is-full .full\:w-full,.is-lite .lite\:w-full{width:100%}.page-form{--panel-container-width:960px;--panel-container-padding:20px;--zt-panel-form-max-width:1200px;--zt-panel-form-min-width:1040px;padding-left:0;padding-right:0;--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.page-form .panel-heading{border-bottom-width:1px;--tw-border-opacity:0.7;padding:0}.page-form .panel-title{font-size:1rem;line-height:1.5rem}@media (max-width:1240px){.page-form{--zt-panel-form-max-width:1100px}}@media (max-width:1110px){.page-form{--zt-panel-form-max-width:1040px}}.modal-body>.page-form{margin:-1.5rem -2rem!important;--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000;box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.modal-body>.page-form>.panel-heading{border-top-left-radius:var(--radius);border-top-right-radius:var(--radius);position:sticky;top:-1.25rem;z-index:2;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding-bottom:.375rem;padding-top:.375rem}.modal-body>.panel-form .form-actions{bottom:-1.5rem!important;padding-bottom:1.5rem;padding-top:1.5rem}.dropdown.popover{display:flex;flex-direction:column;position:absolute;z-index:1200}.dropdown.show{display:flex}.dropdown-menu{display:none;--menu-min-width:7rem;--menu-max-width:20rem}.dropdown-menu.show,.menu-wrapper>.dropdown-menu,.show>.dropdown-menu{display:block}.dropdown>.dropdown-menu,.menu-wrapper .dropdown-menu{position:relative}.popup .popup.search-menu{background-color:var(--menu-bg)}.show>.menu-wrapper{display:flex}.dropdown>.menu-wrapper{height:100%}.dropdown>.menu-wrapper .menu-wrapper{position:absolute}.dropdown>.menu-wrapper.is-tree .menu-wrapper{position:relative}.is-contextmenu .is-nested-show>a:not(:hover){--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity))}.is-contextmenu .menu-item.is-nested>.item-inner>.nested-toggle-icon{position:absolute;right:.25rem;top:.375rem}.is-contextmenu .menu-nested .menu-item>.item-inner{padding-left:.5rem;padding-right:1.25rem}.is-contextmenu .menu-nested .menu-item>.item-inner>.item-content{overflow:hidden}.dropdown>.arrow{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.global-search-panel li:not(.order-first):hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.global-search-panel li a{width:100%}.global-search-panel li{cursor:pointer}.history-panel>.panel-heading+.panel-body{margin-top:-.75rem}.history-panel-action{position:relative}.history-panel-action:before{border-left-width:1px;bottom:-.375rem;left:.5rem;position:absolute;top:22px;--tw-border-opacity:1;border-color:rgba(var(--color-border-rgb),var(--tw-border-opacity));--tw-content:"";content:var(--tw-content)}.col-reverse>.history-panel-action:first-child:before,.col>.history-panel-action:last-child:before{display:none}.history-panel-action>.item-inner{padding-left:1.5rem}.history-panel-action>.item-inner>.avatar{left:0;position:absolute;top:.375rem}.img-cutter{background:var(--color-gray-100);border:1px solid #ddd;margin-bottom:20px;padding:10px}.img-cutter .canvas{margin:0 auto;max-width:100%;min-width:50px;position:relative}.img-cutter .cover{bottom:0;left:0;position:absolute;right:0;top:0;z-index:1}.img-cutter .controller{background:none;border:1px dashed hsla(0,0%,100%,.7);cursor:move;position:absolute;z-index:5}.img-cutter .control{background:#000;background:rgba(0,0,0,.6);border:1px solid hsla(0,0%,100%,.6);height:6px;position:absolute;width:6px}.img-cutter .control[data-type=left]{cursor:w-resize;left:-4px;margin-top:-3px;top:50%}.img-cutter .control[data-type=top]{cursor:n-resize;left:50%;margin-left:-3px;top:-4px}.img-cutter .control[data-type=right]{cursor:e-resize;margin-top:-3px;right:-4px;top:50%}.img-cutter .control[data-type=bottom]{bottom:-4px;cursor:s-resize;left:50%;margin-left:-3px}.img-cutter .control[data-type=top-left]{cursor:nw-resize;left:-4px;top:-4px}.img-cutter .control[data-type=top-right]{cursor:ne-resize;right:-4px;top:-4px}.img-cutter .control[data-type=bottom-left]{bottom:-4px;cursor:sw-resize;left:-4px}.img-cutter .control[data-type=bottom-right]{bottom:-4px;cursor:se-resize;right:-4px}.img-cutter .cliper{bottom:0;left:0;position:absolute;right:0;top:0;z-index:2}.messager-lite{border-radius:var(--radius-lg);min-width:160px;--tw-bg-opacity:1!important;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))!important;padding:1rem 1.5rem;--tw-text-opacity:1!important;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))!important;--skin-ring:transparent!important;--skin-text:inherit!important;--skin-color:var(--color-gray-500)}.messager-lite .alert-icon{color:var(--skin-color);font-size:1.5rem;line-height:2rem}.messager-lite .alert-text{font-size:.875rem;font-weight:700;line-height:1.3rem}.messager-lite .toolbar{gap:.5rem;margin-left:2rem}.messager-lite .alert-content+.alert-close{margin-left:1.5rem}.messager-lite .toolbar .btn.ghost{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.modal-reconfirm .modal-body{font-size:14px;font-weight:700;padding:24px 32px}.modal-reconfirm .modal-footer{justify-content:center;padding:24px}.picker-deselect-btn{opacity:.6;transition-duration:.15s;transition-property:opacity,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.picker-multi-selection{cursor:pointer;padding-right:.5rem;position:relative}.picker-multi-selection .picker-deselect-btn{bottom:0;left:0;position:absolute;right:0;top:0;--tw-scale-x:0;--tw-scale-y:0;background-color:rgba(var(--color-surface-rgb),.8);opacity:0}.picker-deselect-btn:hover,.picker-multi-selection .picker-deselect-btn,.picker-multi-selection:hover .picker-deselect-btn{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.picker-deselect-btn:hover,.picker-multi-selection:hover .picker-deselect-btn{--tw-scale-x:1;--tw-scale-y:1;opacity:1;--state-color:rgba(var(--color-surface-rgb),.9)}.pick-pri{flex-direction:row;justify-content:flex-start;position:relative}.pick-pri,.pick-pri>.text{align-items:center;display:flex}.pick-pri>.text{flex:1 1 auto;min-width:0;overflow:hidden;white-space:nowrap}.pick-pri .placeholder{--tw-text-opacity:1;color:rgba(var(--color-placeholder-rgb),var(--tw-text-opacity))}.pick-pri-list>.btn{justify-content:flex-start}.disabled.pick-pri,.disabled.pick-pri>*{filter:none}.search-form{--gutter-width:12px;padding-bottom:.5rem}.search-form-container{border-radius:var(--radius);min-height:116px;position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.is-simple .search-form-container{min-height:56px}.search-form-field td{padding:.375rem}.search-form-field td.is-andOr,.search-form-field td.is-operator{width:5rem}.search-form-field td.is-condition{width:7rem}.search-form-field td.is-operator{width:5rem}[lang=en] .search-form-field td.is-operator{width:6rem}.search-form .sidebar-right.is-collapsed{margin-right:-.375rem}.is-simple .search-form-wrapper{display:flex}.is-simple .search-form-wrapper>.row{flex:1 1 auto}.is-simple .search-form-wrapper>.toolbar{flex:none;margin-top:0}.zinbar [data-hint]{position:relative}.zinbar [data-hint]:after{background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity));border-top-left-radius:var(--radius-lg);border-top-right-radius:var(--radius-lg);bottom:100%;display:block;pointer-events:none;position:absolute;right:0;white-space:nowrap;z-index:50;--tw-bg-opacity:0.9;font-size:.75rem;line-height:1rem;padding:.125rem .25rem;--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity));opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);--tw-content:attr(data-hint);content:var(--tw-content)}.zinbar [data-hint]:hover:after{opacity:1}.zin-perf-btn-list .text-danger{color:var(--color-danger-400)}.zinbar .state{transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.zinbar .state:active{--tw-scale-x:1.05;--tw-scale-y:1.05}.zinbar .state:active,.zinbar.collapse{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.zinbar.collapse{--tw-translate-x:100%}.zinbar.collapse>div{pointer-events:none}.zinbar{--tw-translate-x:0px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));transition-duration:.7s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}body[z-perf=danger]:before,body[z-perf=warning]:before{bottom:0;left:0;pointer-events:none;position:fixed;right:0;top:0;z-index:9990;--tw-border-opacity:1;border-color:rgba(var(--color-warning-600-rgb),var(--tw-border-opacity));font-size:.75rem;line-height:1rem;--tw-content:"";border-style:inset;border-width:12px 8px 8px;content:var(--tw-content)}body[z-perf=danger]:before{--tw-border-opacity:1;border-color:rgba(var(--color-danger-600-rgb),var(--tw-border-opacity))}body[z-perf=danger]:after,body[z-perf=warning]:after{font-size:.75rem;font-weight:700;left:0;line-height:1rem;line-height:1;pointer-events:none;position:fixed;right:0;text-align:center;top:0;z-index:9991;--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity));--tw-content:attr(z-perf-message);content:var(--tw-content)}.card{border-radius:var(--radius);min-height:28px;position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;transition-duration:.15s;transition-property:box-shadow,border,color,background-color;transition-timing-function:cubic-bezier(.4,0,.2,1)}.card:hover{--tw-shadow:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--tw-shadow-colored:0 2px 6px -1px var(--tw-shadow-color),0 1px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.card-content,.card-footer,.card-header,.card-heading{padding:.25rem .5rem}.card-heading{align-items:center;display:flex;gap:.5rem}.card-icon{opacity:.5}.card-header{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.card-content{display:flex;flex-direction:column;gap:.25rem}.card-actions{position:absolute;right:.125rem;top:.125rem}.card-actions+.card-heading{padding-right:1.75rem}.card-subtitle{font-size:.75rem;line-height:1rem;--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.card.selected{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-400-rgb),var(--tw-ring-opacity))}.card-list{--list-gap:.625rem;--list-count-per-row:1}.card-list,.card-list-item{padding:calc(var(--list-gap)/2)}.card-list-item{width:calc(100%/var(--list-count-per-row))}.card-grid{display:flex;flex-wrap:wrap}.card-grid .card{height:100%}.contextmenu{display:none}.contextmenu.show{display:block}.contextmenu .popup .popup,.contextmenu.popup{position:absolute}.more,.more-vert{margin:.5rem;position:relative}.more,.more-vert,.more-vert:after,.more-vert:before,.more:after,.more:before{background-color:currentColor;border-radius:var(--radius-full);height:.125rem;width:.125rem}.more-vert:after,.more-vert:before,.more:after,.more:before{display:block;left:-5px;position:absolute;top:0;--tw-content:"";content:var(--tw-content)}.more-vert:after,.more:after{left:5px}.more-vert{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dashboard-blocks{position:relative}.dashboard-block-cell{position:absolute;transition-duration:.15s;transition-property:left,top;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-block{border-radius:var(--radius);bottom:.5rem;left:.5rem;position:absolute;right:.5rem;top:.5rem;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-block.is-dragging{opacity:0;z-index:1600}.dashboard-block-header{align-items:center;border-top-left-radius:var(--radius);border-top-right-radius:var(--radius);display:flex;flex-direction:row;justify-content:space-between;left:0;padding:.75rem;pointer-events:none;position:absolute;right:0;top:0;z-index:10}.dashboard-block-header>*{pointer-events:auto}.dashboard-block-title{font-size:.875rem;font-weight:700;line-height:1.3rem}.dashboard-block-body{bottom:0;left:0;position:absolute;right:0;top:0}.dashboard-block-body>.panel{display:flex;flex-direction:column;height:100%;width:100%;--tw-shadow:0px 6px 16px rgba(202,215,235,.25)}.dashboard-block-body .panel-heading{cursor:move;flex:none}.dashboard-block-body .panel-body{flex:1 1 auto;overflow-y:auto}.has-more-menu>.dashboard-block-body .panel-heading{padding-right:3rem}.dashboard-block-body .panel-title{font-size:.875rem;height:2rem;line-height:1.3rem}.dashboard-block-actions .btn{opacity:.6}.dashboard-block-actions .btn:hover{opacity:1}.dashboard-drop-shadow{position:absolute;transition-duration:.15s;transition-property:left,top;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dashboard-drop-shadow:before{background-color:rgba(var(--color-inverse-rgb),.05);border-radius:var(--radius);bottom:.5rem;left:.5rem;position:absolute;right:.5rem;top:.5rem;--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-content:"";content:var(--tw-content)}.scrollbar,:root{--scrollbar-size:10px;--scrollbar-opacity:.6;--scrollbar-bg:rgba(var(--color-inverse-rgb),.15);--scrollbar-inset:inset 0 0 0 1px rgba(var(--color-inverse-rgb),.05);--scrollbar-bar-bg:rgba(var(--color-inverse-rgb),.3);--scrollbar-hover-bg:rgba(var(--color-inverse-rgb),.4);--scrollbar-drag-bg:rgba(var(--color-inverse-rgb),.5);--scrollbar-radius:var(--radius-sm);--scrollbar-duration:.7s}.scrollbar{background:var(--scrollbar-bg);box-shadow:var(--scrollbar-shadow);opacity:var(--scrollbar-opacity);position:absolute;transition-duration:.15s;transition-duration:var(--scrollbar-duration);transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.scrollbar-hover .scrollbar{opacity:0}.scrollbar-hover:hover .scrollbar{opacity:var(--scrollbar-opacity)}.scrollbar.is-dragging,.scrollbar:hover{opacity:1!important}.scrollbar-bar{background:var(--scrollbar-bar-bg);border-radius:var(--scrollbar-radius);position:absolute}.scrollbar-bar:hover{background:var(--scrollbar-hover-bg)}.is-dragging>.scrollbar-bar{background:var(--scrollbar-drag-bg)}.is-horz>.scrollbar-bar{height:100%;z-index:20}.is-vert>.scrollbar-bar{width:100%;z-index:20}:root{--dtable-checked-bg:var(--color-warning-50);--dtable-checked-bg-hover:var(--color-warning-100);--dtable-checked-border:var(--color-border-strong)}.dtable-cell.is-checked,.dtable-striped .dtable-cell.is-odd-row.is-checked{background-color:var(--dtable-checked-bg)}.checkbox-primary.dtable-checkbox{margin-right:-.375rem}.dtable-checkbox{order:-5}.dtable-hover-col .dtable-cell.is-hover-col.is-checked,.dtable-hover-row .dtable-cell.is-hover-row.is-checked{background-color:var(--dtable-checked-bg-hover)}.dtable-cell.is-checked{--dtable-border-color:var(--dtable-checked-border)}.dtable-check-info{flex-shrink:1;margin-right:.5rem;overflow:hidden;white-space:nowrap}:root{--toggle-icon-size:calc(var(--font-size-root)*3/4 + 1px)}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-color:currentColor;border-width:1px;display:block;opacity:.5;position:relative}.toggle-icon-collapse:hover,.toggle-icon-expand:hover,.toggle-icon:hover{opacity:.9}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-radius:inherit;height:var(--toggle-icon-size);width:var(--toggle-icon-size)}.is-collapsed .toggle-icon:after,.is-collapsed .toggle-icon:before,.is-expanded .toggle-icon:before,.toggle-icon-collapse:after,.toggle-icon-collapse:before,.toggle-icon-expand:before{background-color:currentColor;content:" ";display:block;height:1px;left:2px;position:absolute;right:2px;top:calc((var(--toggle-icon-size) - 3px)/2)}.is-collapsed .toggle-icon:after,.toggle-icon-collapse:after{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:root{--dtable-nt-size:calc(var(--font-size-root)*3/4 + 1px)}.dtable-nested-indent{flex:none;margin-right:-.25rem;order:-100}.dtable-nested-toggle{align-items:center;border-radius:var(--radius-sm);display:flex;flex:none;height:1.25rem;justify-content:center;margin-left:-.25rem;order:-6;width:1.25rem}.dtable-nested-toggle.is-no-child{margin-right:-.25rem;opacity:0;pointer-events:none}.dtable-child-label{order:-5}.dtable-header-group{align-items:center;background:var(--dtable-header-bg);cursor:default;display:flex;justify-content:center;left:0;position:absolute;top:1px;z-index:30}.dtable-bordered .dtable-header-group{border-bottom:1px solid var(--dtable-border-color);border-left:1px solid var(--dtable-border-color)}.dtable-header-as-group{contain:style;content-visibility:visible;overflow:visible!important}.dtable-sorting{cursor:move}.dtable-cell.is-sorting-from{background-color:var(--dtable-bg);z-index:20}.dtable-cell.is-sorting-from:before{border-top-width:1px}.dtable-sorting .dtable-cell.is-sorting-after{--tw-translate-y:-100%}.dtable-sorting .dtable-cell.is-sorting-after,.dtable-sorting .dtable-cell.is-sorting-before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dtable-sorting .dtable-cell.is-sorting-before{--tw-translate-y:100%}.dtable-cell.is-sorting-before:before,.dtable-cell.is-sorting-from:before{border-bottom-width:1px;border-top-width:1px}.dtable{--dtable-bg:var(--color-canvas);--dtable-striped-bg:var(--color-gray-50);--dtable-hover-bg:rgba(var(--color-primary-500-rgb),.05);--dtable-header-bg:var(--color-surface);--dtable-footer-bg:var(--color-surface);--dtable-border-color:var(--color-border);--dtable-sorter-size:0.3125rem}.dtable{position:relative;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.dtable.no-animation *{transition-property:none!important}.dtable-block{overflow:hidden;position:absolute;width:100%}.dtable-header{background-color:var(--dtable-header-bg);border-top-left-radius:inherit;border-top-right-radius:inherit}.dtable-body{overflow:hidden}.dtable-cells{background-color:var(--dtable-bg);height:100%;position:absolute;z-index:0}.dtable-cells-container{height:100%;position:absolute;width:100%}.dtable-header .dtable-cells{background-color:var(--dtable-header-bg)}.dtable-cells.dtable-fixed-left,.dtable-cells.dtable-fixed-right{z-index:10}.dtable-cell{position:absolute;transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-cell:after,.dtable-cell:before{bottom:0;content:"";left:0;opacity:0;pointer-events:none;position:absolute;right:0;top:-1px;z-index:2}.dtable-cell:before{border-bottom-width:1px;border-color:var(--dtable-border-color);opacity:1}.dtable-header-cell{align-items:center;display:flex;font-weight:700}.dtable-header-cell:after,.dtable-header-cell:before{top:0}.dtable-cell-content{align-items:center;display:flex;gap:.25rem;height:100%;overflow:hidden;padding-left:.75rem;padding-right:.75rem;position:relative;white-space:nowrap;width:100%;z-index:5}.dtable-body .dtable-cell.is-last-row:before{border-bottom-width:0}.dtable-footer{align-items:center;background-color:var(--dtable-footer-bg);border-bottom-left-radius:inherit;border-bottom-right-radius:inherit;border-color:var(--dtable-border-color);border-top-width:1px;display:flex;padding-left:.75rem;padding-right:.75rem;position:absolute;width:100%;z-index:10}.dtable-empty-tip{align-items:center;display:flex;height:100%;justify-content:center}.dtable .scrollbar{z-index:20}.dtable-header{transition-duration:1s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-scrolled-down .dtable-header{border-bottom-color:rgba(var(--color-inverse-rgb),.15);border-bottom-width:1px}.dtable-has-scroll-y:not(.dtable-scrolled-bottom) .dtable-footer{border-top-color:rgba(var(--color-inverse-rgb),.15);border-top-width:1px}.dtable-scroll-shadow{background-image:linear-gradient(90deg,rgba(0,0,0,.03),transparent),linear-gradient(90deg,rgba(0,0,0,.03),transparent 50%);opacity:0;pointer-events:none;position:absolute;top:0;transition-duration:1s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:8px;z-index:20}.dtable:hover .dtable-scroll-shadow{opacity:1}.dtable-scroll-shadow.is-right{margin-left:-7px;--tw-rotate:180deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.dtable-scroll-shadow.is-left,.dtable-scrolled-end .dtable-scroll-shadow.is-right{visibility:hidden}.dtable-scroll-shadow.is-right,.dtable-scrolled-right .dtable-scroll-shadow.is-left{visibility:visible}.scrollbar-hover:hover .scrollbar{opacity:0}.scrollbar-hover .dtable-body:hover~.scrollbar{opacity:var(--scrollbar-opacity)}.dtable-sort{display:inline-flex;height:calc(var(--dtable-sorter-size)*12/5);margin-left:.25rem;opacity:.8;position:relative}.dtable-cell:hover .dtable-sort{opacity:1}.dtable-sort:after,.dtable-sort:before{border-color:transparent;border-style:solid;height:0;left:0;opacity:.4;position:absolute;width:0;--tw-content:"";border-width:var(--dtable-sorter-size);content:var(--tw-content)}.dtable-sort:before{border-bottom-color:currentColor;border-top-width:0;top:0}.dtable-sort:after{border-bottom-width:0;border-top-color:currentColor;bottom:0}.dtable-sort.dtable-sort-asc:before,.dtable-sort.dtable-sort-desc:after{opacity:.9}.dtable-sort-link{align-items:center;cursor:pointer;display:inline-flex}.dtable-cells.dtable-fixed-left:before,.dtable-cells.dtable-fixed-right:before{border-color:var(--dtable-border-color);content:"";height:100%;pointer-events:none;position:absolute;width:100%;z-index:5}.dtable-cells.dtable-fixed-left:before{border-right-width:1px;right:-1px}.dtable-cells.dtable-fixed-right:before{border-left-width:1px;left:0}.dtable-bordered:before{border-color:var(--dtable-border-color);border-radius:inherit;border-width:1px;bottom:0;content:"";display:block;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:15}.dtable-bordered .dtable-cell:before{border-width:1px;right:-1px}.dtable-cell.has-border-left:before{border-left-width:1px}.dtable-cell.has-border-right:before{border-right-width:1px;right:-1px}.dtable-striped .dtable-cell.is-odd-row{background-color:var(--dtable-striped-bg)}.dtable-hover-cell .dtable-cell:hover:after,.dtable-hover-col .dtable-cell.is-hover-col:before,.dtable-hover-row .dtable-body .dtable-cell.is-hover-row:before{background-color:var(--dtable-hover-bg)}.kanban{--kanban-lane-name-width:20px;--kanban-col-width:280px;--kanban-cols-gap:8px;--kanban-lanes-gap:8px;--kanban-header-height:32px;--kanban-lane-height:auto;--kanban-lane-color:var(--color-primary-500);--kanban-link-color:var(--color-secondary-600)}.kanban{align-items:flex-start;display:flex;flex-direction:column;min-width:-moz-fit-content;min-width:fit-content;position:relative}.kanban-header{display:flex;flex-direction:row;height:var(--kanban-header-height)}.kanban.has-sub-cols .kanban-header{height:calc(var(--kanban-header-height)*2)}.kanban-header-lane-name{background-color:rgba(var(--color-fore-rgb),.05);flex:none;width:var(--kanban-lane-name-width)}.kanban-header-cols,.kanban-header-sub-cols{display:flex;flex:1 1 0%;flex-direction:row;gap:var(--kanban-cols-gap)}.kanban-header-sub-cols{border-top-width:2px;--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity))}.kanban-header-col{align-items:center;border-bottom-width:1px;display:flex;flex:1 1 0%;flex-direction:column;height:100%;width:var(--kanban-col-width)}.kanban-header-col.has-subs{width:auto}.kanban-header-col-wrapper{align-items:center;display:flex;flex:1 1 0%;flex-direction:row;position:relative;width:100%;--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));padding-left:3.5rem;padding-right:3.5rem}.kanban-header-col-wrapper.is-align-left{justify-content:flex-start;padding-left:.5rem}.kanban-header-col-wrapper.is-align-left>.kanban-header-title{justify-content:flex-start}.kanban-header-title{align-items:center;display:flex;flex:1 1 auto;flex-direction:row;justify-content:center;overflow:hidden}.kanban-header-title>.as-title{color:var(--kanban-col-color);font-weight:700;overflow:hidden;white-space:nowrap}.kanban-header-col-actions{bottom:.25rem;position:absolute;right:.25rem;top:.25rem}.kanban-header-col-actions>.btn{opacity:.6}.kanban-header-col-actions>.btn:hover{opacity:1}.kanban-body{display:flex;flex-direction:column;gap:var(--kanban-lanes-gap)}.kanban-lane{display:flex;flex-direction:row;height:var(--kanban-lane-height);min-height:96px}.kanban-lane-name{align-items:center;background-color:var(--kanban-lane-color);display:flex;justify-content:center;width:var(--kanban-lane-name-width);--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity));writing-mode:vertical-rl}.kanban-lane-actions,.kanban-lane-name{flex:none;position:relative}.kanban-lane.is-first .kanban-lane-actions{margin-top:calc(4px - var(--kanban-header-height))}.has-sub-cols .kanban-lane.is-first .kanban-lane-actions{margin-top:calc(4px - var(--kanban-header-height)*2)}.kanban-lane-actions>.btn.square{width:var(--kanban-lane-name-width)}.kanban-lane-title{align-items:center;display:flex;flex:1 1 auto;justify-content:center;overflow:hidden;white-space:nowrap}.kanban-lane-cols{display:flex;flex-direction:row;gap:var(--kanban-cols-gap)}.kanban-lane-col{background-color:rgba(var(--color-inverse-rgb),.05);display:flex;flex-direction:column;height:100%;width:var(--kanban-col-width)}.kanban-header-col,.kanban-lane-col{margin-left:calc(var(--kanban-col-gap-left) - var(--kanban-cols-gap));margin-right:calc(var(--kanban-col-gap-right) - var(--kanban-cols-gap))}.kanban-col-content{position:relative;z-index:5}.kanban-lane.is-first>.kanban-lane-name:before{background-color:var(--kanban-lane-color);bottom:100%;display:block;height:var(--kanban-header-height);left:0;position:absolute;right:0;--tw-content:"";content:var(--tw-content)}.kanban.has-sub-cols .kanban-lane.is-first>.kanban-lane-name:before{height:calc(var(--kanban-header-height)*2)}.kanban-lane{margin-bottom:calc(var(--kanban-col-gap-bottom) - var(--kanban-lanes-gap));margin-top:calc(var(--kanban-col-gap-top) - var(--kanban-lanes-gap))}.kanban-items{flex:1 1 auto;overflow:auto;scrollbar-gutter:both-edges stable}.kanban-lane.is-auto-height .kanban-items{scrollbar-gutter:auto}.kanban-item{cursor:default}.kanban-item .card-actions{z-index:5}.kanban-heading{width:100%}.kanban-heading .listitem{height:2.25rem}.kanban-heading .item-title{font-weight:700}.kanban.has-dragging{cursor:move}.kanban-item.is-dragging{cursor:move;opacity:.1}.kanban-sticky .kanban-header{position:sticky;top:0;z-index:10;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.kanban-sticky .kanban-header.is-pinned{border-bottom-color:rgba(var(--color-inverse-rgb),.15);border-bottom-width:1px;z-index:20;--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.kanban-sticky .kanban-lane-name{left:0;position:sticky;z-index:21}.kanban-region{border-radius:var(--radius);min-width:-moz-fit-content;min-width:fit-content;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));padding:.75rem;--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.kanban-region>.kanban+.kanban{margin-top:.75rem}.kanban-region.has-heading{padding-top:0}.kanban-heading>.listitem{left:.75rem;position:sticky;width:calc(var(--kanban-list-width) - 24px)}.kanban-list{display:flex;flex-direction:column;gap:.75rem;height:100vh;overflow:auto;position:relative;scrollbar-gutter:stable}.kanban-list.is-moving{cursor:grabbing}.kanban-items.is-dropping{position:relative}.kanban-item.is-dropping{position:relative;transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.kanban-item.is-dropping:after,.kanban-items.is-dropping>.card-list:after{background-color:rgba(var(--color-warning-500-rgb),.5);border-radius:var(--radius-full);display:block;height:.25rem;--tw-content:"";content:var(--tw-content)}.kanban-item.is-dropping:after{left:.25rem;position:absolute;right:.25rem;top:-.25rem}.kanban-item.is-dropping[z-drop-side=before]{--tw-translate-y:0.25rem}.kanban-item.is-dropping[z-drop-side=after],.kanban-item.is-dropping[z-drop-side=before]{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-item.is-dropping[z-drop-side=after]{--tw-translate-y:-0.25rem}.kanban-item.is-dropping[z-drop-side=after]:after{bottom:-.25rem;top:auto}.kanban-links{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:5}.kanban-list>.kanban-links{overflow:visible;z-index:11}.kanban-link{align-items:center;color:var(--kanban-link-color);display:flex;justify-content:center;position:absolute}.kanban-link>svg{position:absolute}.kanban-link-text{border-radius:var(--radius);height:1em;line-height:1;padding-left:.125rem;padding-right:.125rem;pointer-events:auto;position:relative;text-align:center;white-space:nowrap}.kanban-link-start-point{height:.5rem;width:.5rem;--tw-translate-x:-0.25rem;--tw-translate-y:-0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-start-point,.kanban-link-start-point:before{background-color:currentColor;border-radius:var(--radius-full);position:absolute}.kanban-link-start-point:before{bottom:-.25rem;display:block;left:-.25rem;opacity:.2;right:-.25rem;top:-.25rem;--tw-content:"";content:var(--tw-content)}.kanban-link path{pointer-events:auto}.kanban-link path+path{opacity:.6}.kanban-link.is-hover path+path{opacity:1;stroke-width:calc(var(--kanban-link-weight)*1.5)}.kanban-link-delete-btn{pointer-events:auto;--tw-scale-x:.75;--tw-scale-y:.75;opacity:0;transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.is-hover .kanban-link-delete-btn,.kanban-link-delete-btn{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.is-hover .kanban-link-delete-btn{--tw-scale-x:1;--tw-scale-y:1;opacity:1}.is-adding-link{cursor:crosshair;-webkit-user-select:none;-moz-user-select:none;user-select:none}.kanban-link-editor{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0;z-index:20}.kanban-link-editor-from,.kanban-link-editor-to{border-radius:var(--radius);--tw-shadow-color:rgb(var(--color-primary-500-rgb));--tw-shadow:var(--tw-shadow-colored);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-500-rgb),var(--tw-ring-opacity))}.kanban-link-editor-from,.kanban-link-editor-point,.kanban-link-editor-to{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);position:absolute}.kanban-link-editor-point{height:.5rem;pointer-events:auto;width:.5rem;--tw-translate-x:-0.25rem;--tw-translate-y:-0.25rem;border-radius:var(--radius-full);cursor:move;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));opacity:.5;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(4px + var(--tw-ring-offset-width)) var(--tw-ring-color);--tw-ring-color:rgba(var(--color-primary-500-rgb),0.1);transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.kanban-link-editor-point.is-left{left:0;top:50%}.kanban-link-editor-point.is-right{right:0;top:50%;--tw-translate-x:0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-editor-point.is-top{left:50%;top:0}.kanban-link-editor-point.is-bottom{bottom:0;left:50%;--tw-translate-y:0.25rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.kanban-link-editor-point:hover{opacity:1;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(8px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-primary-500-rgb),0.5)}.tab-pane{display:none}.tab-pane.active{display:block}.has-sorting-col{cursor:move;--dtable-sorting-col-color:var(--color-primary-300);--dtable-hover-bg:transparent}.has-sorting-col .dtable-col-splitter{display:none}.dtable-cell.is-sorting-col-move{transition-duration:.15s;transition-property:left;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-cell.is-sorting-from-col{transition-duration:.1s}.dtable-cell.is-sorting-from-col:after{background-color:var(--dtable-sorting-col-color)!important;opacity:.1!important}.dtable-cell.is-sorting-from-col:before{border-left:1px solid var(--dtable-sorting-col-color);border-right:1px solid var(--dtable-sorting-col-color)}.dtable-header-cell.is-sortable-col{cursor:move}.has-sorting-col .scrollbar.is-horz{opacity:var(--scrollbar-opacity)!important}.has-sorting-col .dtable-scroll-shadow{visibility:visible}:root{--dtable-col-splitter-width:7px;--dtable-col-splitter-color:var(--color-primary-500)}.dtable-cell.has-col-resizing:after,.dtable-cell.has-col-splitter:hover:after{background:var(--dtable-col-splitter-color);opacity:.05}.dtable-col-splitter{background:var(--dtable-col-splitter-color);border-radius:var(--radius-full);bottom:0;cursor:ew-resize;opacity:0;position:absolute;right:calc(var(--dtable-col-splitter-width)/-2);top:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1);width:var(--dtable-col-splitter-width);z-index:20}.dtable-cell.has-col-splitter:hover .dtable-col-splitter{opacity:.3}.dtable-cell.has-col-resizing .dtable-col-splitter,.dtable-cell.has-col-splitter .dtable-col-splitter:hover{opacity:.5}.dtable.has-col-resizing .dtable-cell.has-col-splitter:not(.has-col-resizing) .dtable-col-splitter,.dtable.has-col-resizing .dtable-cell.has-col-splitter:not(.has-col-resizing):after{opacity:0}.dtable-col-splitter:after,.dtable-col-splitter:before{content:" ";display:block;height:.5rem;left:50%;margin-top:-.25rem;position:absolute;top:50%;width:1px;--tw-bg-opacity:1;background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity))}.dtable-col-splitter:before{margin-left:-1px}.dtable-col-splitter:after{margin-left:1px}.dtable.has-col-resizing{--dtable-hover-bg:transparent}.dtable.has-col-resizing,.has-col-resizing .dtable-header-cell{cursor:ew-resize!important}.dtable-cell.is-col-resizing:before{border-right:1px solid var(--dtable-col-splitter-color)}.dtable-cell.is-col-resizing:after{background:var(--dtable-col-splitter-color);opacity:.05}.has-col-resizing .scrollbar.is-horz{opacity:var(--scrollbar-opacity)!important}.dtable-cell.has-contextmenu-show:after{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));opacity:.1}.dtable{--dtable-header-bg:var(--color-surface-light);--dtable-footer-bg:var(--color-surface-light);--dtable-border-color:var(--color-border-light);--dtable-checked-border:var(--color-border);--dtable-checked-bg:var(--color-primary-50);--dtable-checked-bg-hover:var(--color-primary-100);--dtable-hover-bg:rgba(var(--color-gray-500-rgb),.05);--dtable-link-color:var(--color-link);--dtable-link-hover-color:var(--color-link-hover);--dtable-link-visited-color:var(--color-link-visited)}.dtable-cell-content[style*="--color-link"]{--dtable-link-hover-color:var(--color-link);--dtable-link-visited-color:var(--color-link)}.dtable-body .dtable-cell a{--dtable-link-color:var(--color-link)}.dtable-body .dtable-cell a:not(.btn){color:var(--dtable-link-color)}.dtable-body .dtable-cell a:not(.btn):visited{color:var(--dtable-link-visited-color)}.dtable-body .dtable-cell a:not(.btn):hover{color:var(--dtable-link-hover-color)}.dtable .btn-avatar{border-radius:var(--radius-full);gap:.25rem;height:1.25rem;--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity));padding-left:0;padding-right:.5rem;--tw-ring-color:transparent}.dtable .btn-avatar:hover{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.dtable-nested-toggle{width:1rem}.dtable .toggle-icon{--toggle-icon-size:11px;border-radius:var(--radius);--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.dtable .toggle-icon:after,.dtable .toggle-icon:before{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-700-rgb),var(--tw-bg-opacity))}.dtable-footer>.toolbar{margin-right:.5rem}.dtable-header .dtable-cell[data-sort]>.dtable-cell-content>a:not(:hover){color:inherit}.dtable-assign-btn{align-items:center;border-radius:var(--radius-full);display:flex;flex-direction:row;height:1.25rem;padding-left:.375rem;padding-right:.375rem;--dtable-link-color:var(--color-fore)}.dtable-assign-btn:not(:hover){color:inherit}.dtable-assign-btn.is-me{--dtable-link-color:var(--color-warning-500)!important}.dtable-assign-btn:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.dtable-assign-btn>span{border-radius:var(--radius-full);line-height:20px;padding-left:.375rem;padding-right:.375rem}.dtable-assign-btn.is-unassigned>span{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity));--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.dtable-assign-btn.is-unassigned:hover>span{background-color:inherit;color:inherit;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.dtable-assign-btn>.icon{opacity:0;transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.dtable-assign-btn:not(.disabled):hover>.icon{opacity:1}.dtable-header .dtable-cell[data-type=assign]{padding-left:1.5rem}.dtable-cell-icon{order:-5}.dtable-custom-cell[data-type=control]{align-items:center;display:flex;justify-content:center;padding-left:.125rem;padding-right:.125rem;z-index:1}.dtable-empty-tip{min-height:212px}.dtable-cell[data-type=actions] .btn>.icon{font-size:1rem;line-height:1.5rem}.menu.menu-dtable-actions.has-icons{align-items:center;display:flex;gap:.25rem;min-width:auto;--menu-icon-opacity:1}.menu.menu-dtable-actions.has-icons>.menu-item>a{padding-left:.25rem;padding-right:.25rem}.menu.menu-dtable-actions.has-icons>.menu-item>a>.icon-EMPTY,.menu.menu-dtable-actions.has-icons>.menu-item>a>.item-content{display:none}.menu.menu-dtable-actions.has-icons>.menu-item>a>.icon-EMPTY+.item-content,.menu.menu-dtable-actions.has-icons>.menu-item>a>.item-content:first-child{display:block}:root{--state-color:rgba(0,0,0,.03);--zt-page-bg:#f8f9fa;--zt-header-height:3rem;--zt-header-bg:var(--color-canvas);--zt-header-color:var(--color-fore);--zt-sidebar-width:160px;--zt-navbar-active-color:var(--color-primary-500)}body{background-color:var(--zt-page-bg)}.page-app{overflow:overlay}.container{min-width:1200px}#header{height:var(--zt-header-height);--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);background:var(--zt-header-bg);border-bottom:1px solid var(--zt-header-border,rgba(var(--color-inverse-rgb),.05));box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);color:var(--zt-header-color)}#header>.container{height:100%;position:relative}#heading{align-items:center;bottom:0;display:flex;gap:.25rem;left:1rem;position:absolute;top:0}#heading>.toolbar{margin-left:-.75rem}#heading .dropmenu-btn>.text{max-width:142px}#heading>[data-zui-dropmenu]+div .dropmenu-btn>.text,#heading>[data-zui-dropmenu]+div+div .dropmenu-btn>.text{max-width:78px}#navbar{align-items:center;display:flex;font-size:.875rem;height:100%;justify-content:center;line-height:1.3rem;--state-color:rgba(var(--color-primary-500-rgb),.05);--state-active-opacity:1;--state-active-color:rgba(var(--color-primary-500-rgb),.08)}#navbar>.nav{--nav-active-color:var(--zt-navbar-active-color,var(--color-current));--nav-item-padding:12px;--nav-divider-margin:8px;margin-left:var(--nav-offset-left)}#navbar>.nav>.nav-item>a{height:3rem;padding-left:var(--nav-item-padding);padding-right:var(--nav-item-padding)}#navbar>.nav>.nav-item>a:before{--tw-scale-x:1!important;--tw-scale-y:1!important;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))!important;--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color)!important;--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)!important;box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)!important}#navbar>.nav>.nav-item>a.active:before{background:var(--state-active-color)!important;opacity:1!important}#navbar>.nav>.divider{align-self:center;height:1.25rem;margin-left:var(--nav-divider-margin);margin-right:var(--nav-divider-margin);opacity:.2}#navbar>.nav.compact{font-size:.8125rem;line-height:1.25rem}#navbar>.nav.compact-extra{font-size:.75rem;line-height:1rem}#toolbar{align-items:center;bottom:0;display:flex;gap:.25rem;position:absolute;right:1rem;top:0}#main{min-height:100vh}#header+#main{min-height:calc(100vh - 3rem)}#main>.container{padding-left:1rem;padding-right:1rem;position:relative}@media (min-width:1400px){#header>.container,#main>.container,#mainNavbar>.container{padding-left:2.5rem;padding-right:2.5rem}#heading{left:2.5rem}#toolbar{right:2.5rem}}#mainNavbar{height:2.75rem;--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}#mainNavbar>.container{position:relative}#mainNavbar .nav{bottom:0;height:2.75rem;justify-content:center;left:0;position:absolute;right:0;top:0}#mainNavbar .nav-item{font-size:.875rem;line-height:1.3rem}#mainNavbar .nav-item>a{border-radius:var(--radius)}#mainMenu{gap:1rem;justify-content:space-between;padding-bottom:.75rem;padding-top:.75rem}#featureBar,#mainMenu{align-items:center;display:flex}#featureBar{flex:1 1 auto;gap:.5rem}#actionBar{gap:.5rem}#actionBar>.nav-divider{margin-left:-.25rem;margin-right:-.25rem}#mainContent{padding-top:.75rem}#mainMenu+#mainContent{padding-top:0}#mainContent.row{align-items:stretch;display:flex;gap:1rem;justify-content:space-between}#mainContent.row>*{flex:1 1 auto;min-width:0}#mainContainer.has-sidebar-left{--gutter-left-size:16px}#mainContainer.is-sidebar-left-collapsed{--gutter-left-size:0}.has-sidebar-animation.has-sidebar-left #mainMenu{transition-duration:.15s;transition-property:padding-left;transition-timing-function:cubic-bezier(.4,0,.2,1)}:root{--modal-radius:var(--radius);--avatar-bg:var(--color-gray-200)}.modal-alert .modal-footer{justify-content:center}.modal-dialog{--tw-bg-opacity:1}.modal-content,.modal-dialog{max-height:calc(100vh - 4rem)}.modal-body,.modal-footer,.modal-header{padding:1.5rem 2rem}.modal-header{padding-right:3rem}.modal-body+.modal-footer,.modal-header+.modal-actions+.modal-body,.modal-header+.modal-body{padding-top:1px}.modal-condensed .modal-body,.modal-condensed .modal-header{padding:1rem 1.25rem}.modal-condensed .modal-actions{top:.75rem}:root{--label-bg:var(--color-gray-100);--label-color:var(--color-gray-800)}.label[class$=-pale],.label[class*="-pale "]{--tw-bg-opacity:0.4;--tw-ring-opacity:0.4}.body-modal .panel-form,.modal-body>.panel-form{margin:0;padding:0}.modal-body>.panel-form>.panel-heading{padding-left:1px;padding-right:1px;padding-top:1px}.modal-body>.panel-form>.panel-body{padding:1px}.modal-body>.form{padding-top:1px}.modal .history,.modal .panel-body>.form{padding:0}:root{--article-p-space:0}.lane-col-join-with-above{position:relative}.lane-col-join-with-above:before{background-color:inherit;left:0;position:absolute;right:0;--tw-content:"";content:var(--tw-content);height:var(--kanban-col-gap-top,var(--kanban-lanes-gap));top:calc(0px - var(--kanban-col-gap-top, var(--kanban-lanes-gap)))}.arrow,.arrow:before{background:inherit;height:calc(var(--arrow-size)*1.4142);position:absolute;width:calc(var(--arrow-size)*1.4142)}.arrow{visibility:hidden;--arrow-size:5px}.arrow:before{border:inherit;content:"";visibility:visible;--tw-rotate:45deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.arrow-top,.arrow-up{border-bottom:inherit;border-right:inherit;border-width:1px 0 0 1px;top:calc(1px - var(--arrow-size))}.white>.arrow-top,.white>.arrow-up{top:calc(0px - var(--arrow-size))}.arrow-bottom,.arrow-down{border-left:inherit;border-top:inherit;border-width:0 1px 1px 0;bottom:calc(1px - var(--arrow-size))}.white>.arrow-bottom,.white>.arrow-down{bottom:calc(0px - var(--arrow-size))}.arrow-left{border-right:inherit;border-top:inherit;border-width:0 0 1px 1px;left:calc(1px - var(--arrow-size))}.white>.arrow-left{left:calc(0px - var(--arrow-size))}.arrow-right{border-bottom:inherit;border-left:inherit;border-width:1px 1px 0 0;right:calc(1px - var(--arrow-size))}.white>.arrow-right{right:calc(0px - var(--arrow-size))}.caret,.caret-down,.caret-left,.caret-right,.caret-up{align-items:center;display:inline-flex;height:.75rem;justify-content:center;position:relative;width:.75rem}.caret-down:before,.caret-left:before,.caret-right:before,.caret-up:before,.caret:before{display:block;height:.35rem;transform-origin:center;width:.35rem;--tw-translate-y:-1px;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.caret-left:before{--tw-translate-x:0.125rem;--tw-translate-y:0px;--tw-rotate:135deg}.caret-left:before,.caret-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.caret-right:before{--tw-translate-x:-0.125rem;--tw-translate-y:0px;--tw-rotate:-45deg}.caret-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}:focus>.caret,:hover>.caret{opacity:inherit}.disabled .caret,.readonly .caret{opacity:var(--caret-opacity,.5)}:root{--toggle-icon-size:calc(var(--font-size-root)*3/4 + 1px)}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-color:currentColor;border-width:1px;display:block;opacity:.5;position:relative}.toggle-icon-collapse:hover,.toggle-icon-expand:hover,.toggle-icon:hover{opacity:.9}.toggle-icon,.toggle-icon-collapse,.toggle-icon-expand{border-radius:inherit;height:var(--toggle-icon-size);width:var(--toggle-icon-size)}.is-collapsed .toggle-icon:after,.is-collapsed .toggle-icon:before,.is-expanded .toggle-icon:before,.toggle-icon-collapse:after,.toggle-icon-collapse:before,.toggle-icon-expand:before{background-color:currentColor;content:" ";display:block;height:1px;left:2px;position:absolute;right:2px;top:calc((var(--toggle-icon-size) - 3px)/2)}.is-collapsed .toggle-icon:after,.toggle-icon-collapse:after{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close{aspect-ratio:1/1;display:block;position:relative;width:1em}.close:after,.close:before{content:"";display:block;height:1px;left:0;position:absolute;width:100%;--tw-rotate:45deg;background-color:currentColor;border-radius:var(--radius-full);top:calc(50% - .5px)}.close:after,.close:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.close:after{--tw-rotate:-45deg}.spinner,.spinner:after,.spinner:before{display:block;height:1em;position:relative;width:1em}.spinner:after,.spinner:before{border-radius:var(--radius-full);content:" ";position:absolute}.spinner:before{animation:-spin 1s cubic-bezier(.6,0,.4,1) infinite;border:.16667em solid transparent;border-top-color:currentcolor}.spinner:after{border:.16667em solid;opacity:.2}.magnifier{display:inline-block;height:1em;position:relative;width:1em}.magnifier:after,.magnifier:before{border-radius:var(--radius-full);content:"";display:block;position:absolute}.magnifier:before{border:1px solid;height:.75em;width:.75em}.magnifier:after{height:1px;left:.55em;top:.7em;width:.5em;--tw-rotate:45deg;background-color:currentColor;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.more,.more-vert{margin:.5rem;position:relative}.more,.more-vert,.more-vert:after,.more-vert:before,.more:after,.more:before{background-color:currentColor;border-radius:var(--radius-full);height:.125rem;width:.125rem}.more-vert:after,.more-vert:before,.more:after,.more:before{display:block;left:-5px;position:absolute;top:0;--tw-content:"";content:var(--tw-content)}.more-vert:after,.more:after{left:5px}.more-vert{--tw-rotate:90deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-down,.chevron-left,.chevron-right,.chevron-up{align-items:center;display:inline-flex;height:1em;justify-content:center;position:relative;width:1em}.chevron-down:before,.chevron-left:before,.chevron-right:before,.chevron-up:before{display:block;height:.6923077em;transform-origin:center;width:.6923077em;--tw-translate-y:-0.125rem;--tw-rotate:45deg;border-color:currentColor;border-width:0 1px 1px 0;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-content:"";content:var(--tw-content)}.chevron-left:before{--tw-translate-y:0px;--tw-translate-x:0.125rem;--tw-rotate:135deg}.chevron-left:before,.chevron-right:before{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.chevron-right:before{--tw-translate-y:0px;--tw-translate-x:-0.125rem;--tw-rotate:-45deg}.chevron-up:before{--tw-translate-y:0.125rem;--tw-rotate:225deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.i-time{border-color:currentColor;border-radius:50%;border-width:.08em;display:inline-block;height:1em;position:relative;width:1em}.i-time:after{border-color:currentColor;border-width:0 0 .08em .08em;height:.385em;left:.3846em;position:absolute;top:.08em;width:.385em;--tw-content:"";content:var(--tw-content)}.i-calendar{border-color:currentColor;border-radius:2px;border-width:.08em;display:inline-block;height:.79em;margin-top:.16em;position:relative;width:1em}.i-calendar:after,.i-calendar:before{border-color:currentColor;border-width:.08em;position:absolute;--tw-content:"";content:var(--tw-content)}.i-calendar:before{border-bottom-width:0;left:.15em;top:.307em;width:.6em}.i-calendar:after{border-bottom-width:0;border-top-width:0;height:.3077em;left:.17em;top:-.154em;width:.538em}:root{--state-color:rgba(0,0,0,.05);--state-scale:.9;--opacity-disabled:.7;--opacity-muted:.5;--load-indicator-duration:300ms;--load-indicator-delay:.5s}.btn,.item>a,.state{cursor:pointer;position:relative}.btn:before,.item>a:before,.state:before{background:var(--state-color);border-radius:inherit;bottom:0;content:" ";display:block;left:0;opacity:0;pointer-events:none;position:absolute;right:0;top:0;transform:scale(var(--state-scale));transition-duration:.2s;transition-property:opacity,transform,box-shadow,background-color;transition-timing-function:cubic-bezier(.4,0,.2,1)}.btn.active:not(:hover,:focus-visible,:focus-within,:active):before,.item>a.active:not(:hover,:focus-visible,:focus-within,:active):before,.state.active:not(:hover,:focus-visible,:focus-within,:active):before{background:var(--state-active-color,var(--state-color));opacity:var(--state-active-opacity,0);--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y));--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);transition-duration:.7s}.btn.selected:not(:hover,:focus-visible,:focus-within,:active):before,.item>a.selected:not(:hover,:focus-visible,:focus-within,:active):before,.state.selected:not(:hover,:focus-visible,:focus-within,:active):before{background:var(--state-selected-color,var(--state-scale));opacity:var(--state-selected-opacity,.1);--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.btn:focus-visible,.item>a:focus-visible,.state:focus-visible{outline:2px solid transparent;outline-offset:2px}.btn:active:before,.btn:focus-visible:before,.btn:hover:before,.item>a:active:before,.item>a:focus-visible:before,.item>a:hover:before,.state:active:before,.state:focus-visible:before,.state:hover:before{--tw-scale-x:1;--tw-scale-y:1;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.btn:hover:before,.item>a:hover:before,.state:hover:before{opacity:var(--state-hover-opacity,1)}.btn:active:before,.item>a:active:before,.state:active:before{background:var(--state-pressed-color,var(--state-color));opacity:var(--state-pressed-opacity,.6);--tw-ring-color:var(--state-ring-color,currentColor);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);transition-duration:.7s}.btn:focus-visible:before,.item>a:focus-visible:before,.state:focus-visible:before{background:var(--state-focus-color,var(--state-color));opacity:var(--state-focus-opacity,1);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-focus-rgb),var(--tw-ring-opacity))}.btn.disabled:before,.btn[disabled]:before,.item>a.disabled:before,.item>a[disabled]:before,.state.disabled:before,.state[disabled]:before{display:none}.btn{--state-active-opacity:1}@-moz-document url-prefix(){.btn,:root{--state-active-opacity:0;--state-focus-opacity:0}}.disabled,.disabled *,[disabled],[disabled] *{cursor:not-allowed!important;opacity:var(--opacity-disabled);--tw-grayscale:grayscale(100%);filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.load-indicator:after,.load-indicator:before{display:block;opacity:0;position:absolute;transition-delay:0s;transition-duration:.15s;transition-duration:var(--load-indicator-duration);transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);visibility:hidden}.load-indicator:before{align-items:center;background-color:rgba(var(--color-canvas-rgb),.7);border-radius:inherit;bottom:0;display:flex;font-size:.75rem;justify-content:center;left:0;line-height:1rem;right:0;top:0;z-index:99;--tw-content:attr(data-loading);content:var(--tw-content)}.load-indicator[data-loading]:before{padding-top:3.5rem}.load-indicator:after{border-color:transparent currentcolor currentcolor;border-radius:var(--radius-full);border-style:dotted;border-width:4px 3px 4px 4px;height:2rem;left:50%;margin-left:-1rem;margin-top:-1rem;top:50%;width:2rem;z-index:100;--tw-content:"";content:var(--tw-content)}.load-indicator.loading:after,.load-indicator.loading:before{opacity:1;transition-delay:var(--load-indicator-delay);visibility:visible}@keyframes -spin{to{transform:rotate(1turn)}}.load-indicator.loading:after{animation:-spin 1s linear infinite;opacity:.5}.events-none,.pointer-events-none{pointer-events:none}.events-auto,.pointer-events-auto{pointer-events:auto}.scroll-auto{scroll-behavior:auto}.scroll-smooth{scroll-behavior:smooth}.select-none{-webkit-user-select:none;-moz-user-select:none;user-select:none}.select-text{-webkit-user-select:text;-moz-user-select:text;user-select:text}.select-all{-webkit-user-select:all;-moz-user-select:all;user-select:all}.select-auto{-webkit-user-select:auto;-moz-user-select:auto;user-select:auto}.cursor-auto{cursor:auto}.cursor-default{cursor:default}.cursor-pointer{cursor:pointer}.cursor-wait{cursor:wait}.cursor-text{cursor:text}.cursor-move{cursor:move}.cursor-help{cursor:help}.cursor-not-allowed{cursor:not-allowed}.active\:opacity-100.active,.active\:opacity-100:active,.group.active .group-active\:opacity-100,.group:active .group-active\:opacity-100,.group:hover .group-hover\:opacity-100,.hover\:opacity-100:hover{opacity:1}.active\:opacity-0.active,.active\:opacity-0:active,.group.active .group-active\:opacity-0,.group:active .group-active\:opacity-0,.group:hover .group-hover\:opacity-0,.hover\:opacity-0:hover{opacity:0}.active\:text-primary.active,.active\:text-primary:active,.group.active .group-active\:text-primary,.group:active .group-active\:text-primary,.group:hover .group-hover\:text-primary,.hover\:text-primary:hover{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.active\:border-primary.active,.active\:border-primary:active,.group.active .group-active\:border-primary,.group:active .group-active\:border-primary,.group:hover .group-hover\:border-primary,.hover\:border-primary:hover{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity))}.active\:primary-pale.active,.active\:primary-pale:active,.group.active .group-active\:primary-pale,.group:active .group-active\:primary-pale,.group:hover .group-hover\:primary-pale,.hover\:primary-pale:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.active\:primary.active,.active\:primary:active,.group.active .group-active\:primary,.group:active .group-active\:primary,.group:hover .group-hover\:primary,.hover\:primary:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.active\:canvas.active,.active\:canvas:active,.group.active .group-active\:canvas,.group:active .group-active\:canvas,.group:hover .group-hover\:canvas,.hover\:canvas:hover{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.active\:font-bold.active,.active\:font-bold:active,.group.active .group-active\:font-bold,.group:active .group-active\:font-bold,.group:hover .group-hover\:font-bold,.hover\:font-bold:hover{font-weight:700}.active\:shadow.active,.active\:shadow:active,.group.active .group-active\:shadow,.group:active .group-active\:shadow,.group:hover .group-hover\:shadow,.hover\:shadow:hover{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.group:hover .group-hover\:block,.hover\:block:hover{display:block!important}.group:hover .group-hover\:flex,.hover\:flex:hover{display:flex!important}.group:hover .group-hover\:inline-flex,.hover\:inline-flex:hover{display:inline-flex!important}.group:hover .group-hover\:scale-110,.hover\:scale-110:hover{--tw-scale-x:1.1!important;--tw-scale-y:1.1!important}.group:hover .group-hover\:scale-110,.group:hover .group-hover\:scale-125,.hover\:scale-110:hover,.hover\:scale-125:hover{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))!important}.group:hover .group-hover\:scale-125,.hover\:scale-125:hover{--tw-scale-x:1.25!important;--tw-scale-y:1.25!important}.aspect-auto{aspect-ratio:auto}.aspect-square{aspect-ratio:1/1}.aspect-video{aspect-ratio:16/9}.container{width:100%}@media (min-width:1720px){.container{max-width:1720px}}.container{margin-left:auto;margin-right:auto}.popup{background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity));border-radius:var(--radius);--tw-bg-opacity:0.85;--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow);--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05;--tw-backdrop-blur:blur(16px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.block{display:block}.inline-block{display:inline-block}.inline{display:inline}.flex{display:flex}.inline-flex{display:inline-flex}.table{display:table}.table-cell{display:table-cell}.table-row{display:table-row}.hidden{display:none!important}.pull-right{float:right}.pull-left{float:left}.clearfix:after{clear:both;content:"";display:block}.object-contain{-o-object-fit:contain;object-fit:contain}.object-cover{-o-object-fit:cover;object-fit:cover}.object-fill{-o-object-fit:fill;object-fit:fill}.object-none{-o-object-fit:none;object-fit:none}.object-scale-down{-o-object-fit:scale-down;object-fit:scale-down}.object-bottom{-o-object-position:bottom;object-position:bottom}.object-center{-o-object-position:center;object-position:center}.object-left{-o-object-position:left;object-position:left}.object-left-bottom{-o-object-position:left bottom;object-position:left bottom}.object-left-top{-o-object-position:left top;object-position:left top}.object-right{-o-object-position:right;object-position:right}.object-right-bottom{-o-object-position:right bottom;object-position:right bottom}.object-right-top{-o-object-position:right top;object-position:right top}.object-top{-o-object-position:top;object-position:top}.overflow-auto{overflow:auto}.overflow-hidden{overflow:hidden}.overflow-clip{overflow:clip}.overflow-visible{overflow:visible}.overflow-scroll{overflow:scroll}.overflow-x-auto{overflow-x:auto}.overflow-y-auto{overflow-y:auto}.overflow-x-hidden{overflow-x:hidden}.overflow-y-hidden{overflow-y:hidden}.overflow-x-clip{overflow-x:clip}.overflow-y-clip{overflow-y:clip}.overflow-x-visible{overflow-x:visible}.overflow-y-visible{overflow-y:visible}.overflow-x-scroll{overflow-x:scroll}.overflow-y-scroll{overflow-y:scroll}.overflow-overlay{overflow:overlay}.static{position:static}.fixed{position:fixed}.absolute{position:absolute}.relative{position:relative}.sticky{position:sticky}.inset-0{bottom:0;left:0;right:0;top:0}.inset-auto{bottom:auto;left:auto;right:auto;top:auto}.inset-x-0{left:0;right:0}.inset-y-0{bottom:0;top:0}.top-0{top:0}.right-0{right:0}.bottom-0{bottom:0}.left-0{left:0}.top-full{top:100%}.right-full{right:100%}.bottom-full{bottom:100%}.left-full{left:100%}.top-auto{top:auto}.right-auto{right:auto}.bottom-auto{bottom:auto}.left-auto{left:auto}.top-px{top:1px}.right-px{right:1px}.bottom-px{bottom:1px}.left-px{left:1px}.top-0\.5{top:.125rem}.right-0\.5{right:.125rem}.bottom-0\.5{bottom:.125rem}.left-0\.5{left:.125rem}.top-1{top:.25rem}.right-1{right:.25rem}.bottom-1{bottom:.25rem}.left-1{left:.25rem}.top-1\.5{top:.375rem}.right-1\.5{right:.375rem}.bottom-1\.5{bottom:.375rem}.left-1\.5{left:.375rem}.top-2{top:.5rem}.right-2{right:.5rem}.bottom-2{bottom:.5rem}.left-2{left:.5rem}.top-2\.5{top:.625rem}.right-2\.5{right:.625rem}.bottom-2\.5{bottom:.625rem}.left-2\.5{left:.625rem}.top-3{top:.75rem}.right-3{right:.75rem}.bottom-3{bottom:.75rem}.left-3{left:.75rem}.top-3\.5{top:.875rem}.right-3\.5{right:.875rem}.bottom-3\.5{bottom:.875rem}.left-3\.5{left:.875rem}.top-4{top:1rem}.right-4{right:1rem}.bottom-4{bottom:1rem}.left-4{left:1rem}.top-5{top:1.25rem}.right-5{right:1.25rem}.bottom-5{bottom:1.25rem}.left-5{left:1.25rem}.top-6{top:1.5rem}.right-6{right:1.5rem}.bottom-6{bottom:1.5rem}.left-6{left:1.5rem}.top-7{top:1.75rem}.right-7{right:1.75rem}.bottom-7{bottom:1.75rem}.left-7{left:1.75rem}.top-8{top:2rem}.right-8{right:2rem}.bottom-8{bottom:2rem}.left-8{left:2rem}.visible{visibility:visible!important}.invisible{visibility:hidden!important}.z-0{z-index:0}.z-1{z-index:1}.z-5{z-index:5}.z-10{z-index:10}.z-20{z-index:20}.z-30{z-index:30}.z-40{z-index:40}.z-50{z-index:50}.z-auto{z-index:auto}.z-base{z-index:1100}.z-above{z-index:50}.z-below{z-index:-50}.z-dropdown{z-index:1200}.z-sticky{z-index:1300}.z-fixed{z-index:1400}.z-modal{z-index:1500}.z-overlay{z-index:1600}.z-popover{z-index:1700}.z-tooltip{z-index:1800}.z-messager{z-index:1900}.m-0{margin:0}.m-auto{margin:auto}.m-px{margin:1px}.m-0\.5{margin:.125rem}.m-1{margin:.25rem}.m-1\.5{margin:.375rem}.m-2{margin:.5rem}.m-2\.5{margin:.625rem}.m-3{margin:.75rem}.m-3\.5{margin:.875rem}.m-4{margin:1rem}.m-5{margin:1.25rem}.m-6{margin:1.5rem}.m-7{margin:1.75rem}.m-8{margin:2rem}.m-9{margin:2.25rem}.m-10{margin:2.5rem}.mx-0{margin-left:0;margin-right:0}.my-0{margin-bottom:0}.mt-0,.my-0{margin-top:0}.mr-0{margin-right:0}.mb-0{margin-bottom:0}.ml-0{margin-left:0}.mx-auto{margin-left:auto;margin-right:auto}.my-auto{margin-bottom:auto}.mt-auto,.my-auto{margin-top:auto}.mr-auto{margin-right:auto}.mb-auto{margin-bottom:auto}.ml-auto{margin-left:auto}.mx-px{margin-left:1px;margin-right:1px}.my-px{margin-bottom:1px}.mt-px,.my-px{margin-top:1px}.mr-px{margin-right:1px}.mb-px{margin-bottom:1px}.ml-px{margin-left:1px}.mx-0\.5{margin-left:.125rem;margin-right:.125rem}.my-0\.5{margin-bottom:.125rem}.mt-0\.5,.my-0\.5{margin-top:.125rem}.mr-0\.5{margin-right:.125rem}.mb-0\.5{margin-bottom:.125rem}.ml-0\.5{margin-left:.125rem}.mx-1{margin-left:.25rem;margin-right:.25rem}.my-1{margin-bottom:.25rem}.mt-1,.my-1{margin-top:.25rem}.mr-1{margin-right:.25rem}.mb-1{margin-bottom:.25rem}.ml-1{margin-left:.25rem}.mx-1\.5{margin-left:.375rem;margin-right:.375rem}.my-1\.5{margin-bottom:.375rem}.mt-1\.5,.my-1\.5{margin-top:.375rem}.mr-1\.5{margin-right:.375rem}.mb-1\.5{margin-bottom:.375rem}.ml-1\.5{margin-left:.375rem}.mx-2{margin-left:.5rem;margin-right:.5rem}.my-2{margin-bottom:.5rem}.mt-2,.my-2{margin-top:.5rem}.mr-2{margin-right:.5rem}.mb-2{margin-bottom:.5rem}.ml-2{margin-left:.5rem}.mx-2\.5{margin-left:.625rem;margin-right:.625rem}.my-2\.5{margin-bottom:.625rem}.mt-2\.5,.my-2\.5{margin-top:.625rem}.mr-2\.5{margin-right:.625rem}.mb-2\.5{margin-bottom:.625rem}.ml-2\.5{margin-left:.625rem}.mx-3{margin-left:.75rem;margin-right:.75rem}.my-3{margin-bottom:.75rem}.mt-3,.my-3{margin-top:.75rem}.mr-3{margin-right:.75rem}.mb-3{margin-bottom:.75rem}.ml-3{margin-left:.75rem}.mx-3\.5{margin-left:.875rem;margin-right:.875rem}.my-3\.5{margin-bottom:.875rem}.mt-3\.5,.my-3\.5{margin-top:.875rem}.mr-3\.5{margin-right:.875rem}.mb-3\.5{margin-bottom:.875rem}.ml-3\.5{margin-left:.875rem}.mx-4{margin-left:1rem;margin-right:1rem}.my-4{margin-bottom:1rem}.mt-4,.my-4{margin-top:1rem}.mr-4{margin-right:1rem}.mb-4{margin-bottom:1rem}.ml-4{margin-left:1rem}.mx-5{margin-left:1.25rem;margin-right:1.25rem}.my-5{margin-bottom:1.25rem}.mt-5,.my-5{margin-top:1.25rem}.mr-5{margin-right:1.25rem}.mb-5{margin-bottom:1.25rem}.ml-5{margin-left:1.25rem}.mx-6{margin-left:1.5rem;margin-right:1.5rem}.my-6{margin-bottom:1.5rem}.mt-6,.my-6{margin-top:1.5rem}.mr-6{margin-right:1.5rem}.mb-6{margin-bottom:1.5rem}.ml-6{margin-left:1.5rem}.mx-7{margin-left:1.75rem;margin-right:1.75rem}.my-7{margin-bottom:1.75rem}.mt-7,.my-7{margin-top:1.75rem}.mr-7{margin-right:1.75rem}.mb-7{margin-bottom:1.75rem}.ml-7{margin-left:1.75rem}.mx-8{margin-left:2rem;margin-right:2rem}.my-8{margin-bottom:2rem}.mt-8,.my-8{margin-top:2rem}.mr-8{margin-right:2rem}.mb-8{margin-bottom:2rem}.ml-8{margin-left:2rem}.mx-9{margin-left:2.25rem;margin-right:2.25rem}.my-9{margin-bottom:2.25rem}.mt-9,.my-9{margin-top:2.25rem}.mr-9{margin-right:2.25rem}.mb-9{margin-bottom:2.25rem}.ml-9{margin-left:2.25rem}.mx-10{margin-left:2.5rem;margin-right:2.5rem}.my-10{margin-bottom:2.5rem}.mt-10,.my-10{margin-top:2.5rem}.mr-10{margin-right:2.5rem}.mb-10{margin-bottom:2.5rem}.ml-10{margin-left:2.5rem}.p-0{padding:0}.p-px{padding:1px}.p-0\.5{padding:.125rem}.p-1{padding:.25rem}.p-1\.5{padding:.375rem}.p-2{padding:.5rem}.p-2\.5{padding:.625rem}.p-3{padding:.75rem}.p-3\.5{padding:.875rem}.p-4{padding:1rem}.p-5{padding:1.25rem}.p-6{padding:1.5rem}.p-7{padding:1.75rem}.p-8{padding:2rem}.p-9{padding:2.25rem}.p-10{padding:2.5rem}.px-0{padding-left:0;padding-right:0}.py-0{padding-bottom:0}.pt-0,.py-0{padding-top:0}.pr-0{padding-right:0}.pb-0{padding-bottom:0}.pl-0{padding-left:0}.px-px{padding-left:1px;padding-right:1px}.py-px{padding-bottom:1px}.pt-px,.py-px{padding-top:1px}.pr-px{padding-right:1px}.pb-px{padding-bottom:1px}.pl-px{padding-left:1px}.px-0\.5{padding-left:.125rem;padding-right:.125rem}.py-0\.5{padding-bottom:.125rem}.pt-0\.5,.py-0\.5{padding-top:.125rem}.pr-0\.5{padding-right:.125rem}.pb-0\.5{padding-bottom:.125rem}.pl-0\.5{padding-left:.125rem}.px-1{padding-left:.25rem;padding-right:.25rem}.py-1{padding-bottom:.25rem}.pt-1,.py-1{padding-top:.25rem}.pr-1{padding-right:.25rem}.pb-1{padding-bottom:.25rem}.pl-1{padding-left:.25rem}.px-1\.5{padding-left:.375rem;padding-right:.375rem}.py-1\.5{padding-bottom:.375rem}.pt-1\.5,.py-1\.5{padding-top:.375rem}.pr-1\.5{padding-right:.375rem}.pb-1\.5{padding-bottom:.375rem}.pl-1\.5{padding-left:.375rem}.px-2{padding-left:.5rem;padding-right:.5rem}.py-2{padding-bottom:.5rem}.pt-2,.py-2{padding-top:.5rem}.pr-2{padding-right:.5rem}.pb-2{padding-bottom:.5rem}.pl-2{padding-left:.5rem}.px-2\.5{padding-left:.625rem;padding-right:.625rem}.py-2\.5{padding-bottom:.625rem}.pt-2\.5,.py-2\.5{padding-top:.625rem}.pr-2\.5{padding-right:.625rem}.pb-2\.5{padding-bottom:.625rem}.pl-2\.5{padding-left:.625rem}.px-3{padding-left:.75rem;padding-right:.75rem}.py-3{padding-bottom:.75rem}.pt-3,.py-3{padding-top:.75rem}.pr-3{padding-right:.75rem}.pb-3{padding-bottom:.75rem}.pl-3{padding-left:.75rem}.px-3\.5{padding-left:.875rem;padding-right:.875rem}.py-3\.5{padding-bottom:.875rem}.pt-3\.5,.py-3\.5{padding-top:.875rem}.pr-3\.5{padding-right:.875rem}.pb-3\.5{padding-bottom:.875rem}.pl-3\.5{padding-left:.875rem}.px-4{padding-left:1rem;padding-right:1rem}.py-4{padding-bottom:1rem}.pt-4,.py-4{padding-top:1rem}.pr-4{padding-right:1rem}.pb-4{padding-bottom:1rem}.pl-4{padding-left:1rem}.px-5{padding-left:1.25rem;padding-right:1.25rem}.py-5{padding-bottom:1.25rem}.pt-5,.py-5{padding-top:1.25rem}.pr-5{padding-right:1.25rem}.pb-5{padding-bottom:1.25rem}.pl-5{padding-left:1.25rem}.px-6{padding-left:1.5rem;padding-right:1.5rem}.py-6{padding-bottom:1.5rem}.pt-6,.py-6{padding-top:1.5rem}.pr-6{padding-right:1.5rem}.pb-6{padding-bottom:1.5rem}.pl-6{padding-left:1.5rem}.px-7{padding-left:1.75rem;padding-right:1.75rem}.py-7{padding-bottom:1.75rem}.pt-7,.py-7{padding-top:1.75rem}.pr-7{padding-right:1.75rem}.pb-7{padding-bottom:1.75rem}.pl-7{padding-left:1.75rem}.px-8{padding-left:2rem;padding-right:2rem}.py-8{padding-bottom:2rem}.pt-8,.py-8{padding-top:2rem}.pr-8{padding-right:2rem}.pb-8{padding-bottom:2rem}.pl-8{padding-left:2rem}.px-9{padding-left:2.25rem;padding-right:2.25rem}.py-9{padding-bottom:2.25rem}.pt-9,.py-9{padding-top:2.25rem}.pr-9{padding-right:2.25rem}.pb-9{padding-bottom:2.25rem}.pl-9{padding-left:2.25rem}.px-10{padding-left:2.5rem;padding-right:2.5rem}.py-10{padding-bottom:2.5rem}.pt-10,.py-10{padding-top:2.5rem}.pr-10{padding-right:2.5rem}.pb-10{padding-bottom:2.5rem}.pl-10{padding-left:2.5rem}.space-x-0>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(0px*(1 - var(--tw-space-x-reverse)));margin-right:calc(0px*var(--tw-space-x-reverse))}.space-y-0>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(0px*var(--tw-space-y-reverse));margin-top:calc(0px*(1 - var(--tw-space-y-reverse)))}.space-x-0\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.125rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.125rem*var(--tw-space-x-reverse))}.space-y-0\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.125rem*var(--tw-space-y-reverse));margin-top:calc(.125rem*(1 - var(--tw-space-y-reverse)))}.space-x-1>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}.space-y-1>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.25rem*var(--tw-space-y-reverse));margin-top:calc(.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-1\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.375rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.375rem*var(--tw-space-x-reverse))}.space-y-1\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.375rem*var(--tw-space-y-reverse));margin-top:calc(.375rem*(1 - var(--tw-space-y-reverse)))}.space-x-2>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.5rem*var(--tw-space-x-reverse))}.space-y-2>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-2\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.625rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.625rem*var(--tw-space-x-reverse))}.space-y-2\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.625rem*var(--tw-space-y-reverse));margin-top:calc(.625rem*(1 - var(--tw-space-y-reverse)))}.space-x-3>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.75rem*var(--tw-space-x-reverse))}.space-y-3>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.75rem*var(--tw-space-y-reverse));margin-top:calc(.75rem*(1 - var(--tw-space-y-reverse)))}.space-x-3\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.875rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.875rem*var(--tw-space-x-reverse))}.space-y-3\.5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.875rem*var(--tw-space-y-reverse));margin-top:calc(.875rem*(1 - var(--tw-space-y-reverse)))}.space-x-4>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1rem*var(--tw-space-x-reverse))}.space-y-4>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.space-x-5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.25rem*var(--tw-space-x-reverse))}.space-y-5>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.25rem*var(--tw-space-y-reverse));margin-top:calc(1.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-6>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.5rem*var(--tw-space-x-reverse))}.space-y-6>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.5rem*var(--tw-space-y-reverse));margin-top:calc(1.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-7>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.75rem*var(--tw-space-x-reverse))}.space-y-7>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.75rem*var(--tw-space-y-reverse));margin-top:calc(1.75rem*(1 - var(--tw-space-y-reverse)))}.space-x-8>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2rem*var(--tw-space-x-reverse))}.space-y-8>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2rem*var(--tw-space-y-reverse));margin-top:calc(2rem*(1 - var(--tw-space-y-reverse)))}.space-x-9>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2.25rem*var(--tw-space-x-reverse))}.space-y-9>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2.25rem*var(--tw-space-y-reverse));margin-top:calc(2.25rem*(1 - var(--tw-space-y-reverse)))}.space-x-10>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2.5rem*var(--tw-space-x-reverse))}.space-y-10>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2.5rem*var(--tw-space-y-reverse));margin-top:calc(2.5rem*(1 - var(--tw-space-y-reverse)))}.space-x-px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1px*(1 - var(--tw-space-x-reverse)));margin-right:calc(1px*var(--tw-space-x-reverse))}.space-y-px>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1px*var(--tw-space-y-reverse));margin-top:calc(1px*(1 - var(--tw-space-y-reverse)))}.w-0{width:0}.w-px{width:1px}.w-0\.5{width:.125rem}.w-1{width:.25rem}.w-1\.5{width:.375rem}.w-2{width:.5rem}.w-2\.5{width:.625rem}.w-3{width:.75rem}.w-3\.5{width:.875rem}.w-4{width:1rem}.w-5{width:1.25rem}.w-6{width:1.5rem}.w-7{width:1.75rem}.w-8{width:2rem}.w-9{width:2.25rem}.w-10{width:2.5rem}.w-11{width:2.75rem}.w-12{width:3rem}.w-14{width:3.5rem}.w-16{width:4rem}.w-20{width:5rem}.w-24{width:6rem}.w-28{width:7rem}.w-32{width:8rem}.w-36{width:9rem}.w-40{width:10rem}.w-44{width:11rem}.w-48{width:12rem}.w-52{width:13rem}.w-56{width:14rem}.w-60{width:15rem}.w-64{width:16rem}.w-72{width:18rem}.w-80{width:20rem}.w-96{width:24rem}.w-1\/2{width:50%}.w-1\/3{width:33.333333%}.w-2\/3{width:66.666667%}.w-1\/4{width:25%}.w-2\/4{width:50%}.w-3\/4{width:75%}.w-1\/5{width:20%}.w-2\/5{width:40%}.w-3\/5{width:60%}.w-4\/5{width:80%}.w-1\/6{width:16.666667%}.w-2\/6{width:33.333333%}.w-3\/6{width:50%}.w-4\/6{width:66.666667%}.w-5\/6{width:83.333333%}.w-auto{width:auto}.w-full{width:100%}.w-screen{width:100vw}.w-min{width:-moz-min-content;width:min-content}.w-max{width:-moz-max-content;width:max-content}.w-fit{width:-moz-fit-content;width:fit-content}.min-w-0{min-width:0}.min-w-full{min-width:100%}.min-w-min{min-width:-moz-min-content;min-width:min-content}.min-w-max{min-width:-moz-max-content;min-width:max-content}.min-w-fit{min-width:-moz-fit-content;min-width:fit-content}.max-w-0{max-width:0}.max-w-none{max-width:none}.max-w-xs{max-width:20rem}.max-w-sm{max-width:24rem}.max-w-md{max-width:28rem}.max-w-lg{max-width:32rem}.max-w-xl{max-width:36rem}.max-w-2xl{max-width:42rem}.max-w-3xl{max-width:48rem}.max-w-4xl{max-width:56rem}.max-w-5xl{max-width:64rem}.max-w-6xl{max-width:72rem}.max-w-7xl{max-width:80rem}.max-w-full{max-width:100%}.max-w-min{max-width:-moz-min-content;max-width:min-content}.max-w-max{max-width:-moz-max-content;max-width:max-content}.max-w-fit{max-width:-moz-fit-content;max-width:fit-content}.h-0{height:0}.h-px{height:1px}.h-0\.5{height:.125rem}.h-1{height:.25rem}.h-1\.5{height:.375rem}.h-2{height:.5rem}.h-2\.5{height:.625rem}.h-3{height:.75rem}.h-3\.5{height:.875rem}.h-4{height:1rem}.h-5{height:1.25rem}.h-6{height:1.5rem}.h-7{height:1.75rem}.h-8{height:2rem}.h-9{height:2.25rem}.h-10{height:2.5rem}.h-11{height:2.75rem}.h-12{height:3rem}.h-14{height:3.5rem}.h-16{height:4rem}.h-20{height:5rem}.h-24{height:6rem}.h-28{height:7rem}.h-32{height:8rem}.h-36{height:9rem}.h-40{height:10rem}.h-44{height:11rem}.h-48{height:12rem}.h-52{height:13rem}.h-56{height:14rem}.h-60{height:15rem}.h-64{height:16rem}.h-72{height:18rem}.h-80{height:20rem}.h-96{height:24rem}.h-1\/2{height:50%}.h-1\/3{height:33.333333%}.h-2\/3{height:66.666667%}.h-1\/4{height:25%}.h-2\/4{height:50%}.h-3\/4{height:75%}.h-1\/5{height:20%}.h-2\/5{height:40%}.h-3\/5{height:60%}.h-4\/5{height:80%}.h-1\/6{height:16.666667%}.h-2\/6{height:33.333333%}.h-3\/6{height:50%}.h-4\/6{height:66.666667%}.h-5\/6{height:83.333333%}.h-auto{height:auto}.h-full{height:100%}.h-screen{height:100vh}.h-min{height:-moz-min-content;height:min-content}.h-max{height:-moz-max-content;height:max-content}.h-fit{height:-moz-fit-content;height:fit-content}.min-h-0{min-height:0}.min-h-full{min-height:100%}.min-h-min{min-height:-moz-min-content;min-height:min-content}.min-h-max{min-height:-moz-max-content;min-height:max-content}.min-h-fit{min-height:-moz-fit-content;min-height:fit-content}.max-h-0{max-height:0}.max-h-px{max-height:1px}.max-h-none{max-height:none}.max-h-full{max-height:100%}.max-h-min{max-height:-moz-min-content;max-height:min-content}.max-h-screen{max-height:100vh}.max-h-max{max-height:-moz-max-content;max-height:max-content}.max-h-fit{max-height:-moz-fit-content;max-height:fit-content}.canvas,.surface,.surface-light,.surface-strong{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}.canvas{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.surface-light{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-light-rgb),var(--tw-ring-opacity))}.surface{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-rgb),var(--tw-ring-opacity))}.surface-strong{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-strong-rgb),var(--tw-bg-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-strong-rgb),var(--tw-ring-opacity))}.inverse{background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity));color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.inverse,.white{--tw-bg-opacity:1;--tw-text-opacity:1}.white{background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity));color:rgba(var(--color-fore-in-light-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-white-rgb),var(--tw-ring-opacity))}.black{--tw-bg-opacity:1;background-color:rgba(var(--color-black-rgb),var(--tw-bg-opacity));--tw-text-opacity:1;color:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity));--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-black-rgb),var(--tw-ring-opacity))}.transparent{background-color:transparent;--tw-ring-color:transparent}.skin{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.skin:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger,.darken,.darker,.darkest,.gray,.gray-100,.gray-200,.gray-300,.gray-400,.gray-50,.gray-500,.gray-600,.gray-700,.gray-800,.gray-900,.gray-950,.important,.lighten,.lighter,.lightest,.primary,.secondary,.special,.success,.warning{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger:hover,.darken:hover,.darker:hover,.darkest:hover,.gray-100:hover,.gray-200:hover,.gray-300:hover,.gray-400:hover,.gray-500:hover,.gray-50:hover,.gray-600:hover,.gray-700:hover,.gray-800:hover,.gray-900:hover,.gray-950:hover,.gray:hover,.important:hover,.lighten:hover,.lighter:hover,.lightest:hover,.primary:hover,.secondary:hover,.special:hover,.success:hover,.warning:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger,.darken,.darker,.darkest,.gray,.gray-100,.gray-200,.gray-300,.gray-400,.gray-50,.gray-500,.gray-600,.gray-700,.gray-800,.gray-900,.gray-950,.important,.lighten,.lighter,.lightest,.primary,.secondary,.special,.success,.warning{--skin-text:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity));--skin-color:rgba(var(--skin-solid-rgb),1);--state-ring-color:var(--skin-color);--state-active-color:rgba(0,0,0,.1);--state-pressed-color:rgba(0,0,0,.1);--state-color:hsla(0,0%,100%,.1);--state-focus-color:rgba(0,0,0,.1)}.primary{--skin-solid-rgb:var(--color-primary-500-rgb)}.secondary{--skin-solid-rgb:var(--color-secondary-500-rgb)}.success{--skin-solid-rgb:var(--color-success-500-rgb)}.warning{--skin-solid-rgb:var(--color-warning-500-rgb)}.danger{--skin-solid-rgb:var(--color-danger-500-rgb)}.important{--skin-solid-rgb:var(--color-important-500-rgb)}.special{--skin-solid-rgb:var(--color-special-500-rgb)}.gray-50{--skin-bg:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity));--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-100{--skin-solid-rgb:var(--color-gray-100-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-200,.lightest{--skin-solid-rgb:var(--color-gray-200-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-300,.lighter{--skin-solid-rgb:var(--color-gray-300-rgb);--skin-text:rgba(var(--color-fore),var(--tw-text-opacity))}.gray-400,.lighten{--skin-solid-rgb:var(--color-gray-400-rgb)}.gray,.gray-500{--skin-solid-rgb:var(--color-gray-500-rgb)}.darken,.gray-600{--skin-solid-rgb:var(--color-gray-600-rgb)}.darker,.gray-700{--skin-solid-rgb:var(--color-gray-700-rgb)}.darkest,.gray-800{--skin-solid-rgb:var(--color-gray-800-rgb)}.gray-900{--skin-solid-rgb:var(--color-gray-900-rgb)}.gray-950{--skin-solid-rgb:var(--color-gray-950-rgb)}.danger-pale,.gray-100-pale,.gray-200-pale,.gray-300-pale,.gray-400-pale,.gray-50-pale,.gray-500-pale,.gray-600-pale,.gray-700-pale,.gray-800-pale,.gray-900-pale,.gray-950-pale,.gray-pale,.important-pale,.pale,.primary-pale,.secondary-pale,.special-pale,.success-pale,.warning-pale{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-pale:hover,.gray-100-pale:hover,.gray-200-pale:hover,.gray-300-pale:hover,.gray-400-pale:hover,.gray-50-pale:hover,.gray-500-pale:hover,.gray-600-pale:hover,.gray-700-pale:hover,.gray-800-pale:hover,.gray-900-pale:hover,.gray-950-pale:hover,.gray-pale:hover,.important-pale:hover,.pale:hover,.primary-pale:hover,.secondary-pale:hover,.special-pale:hover,.success-pale:hover,.warning-pale:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-pale,.gray-100-pale,.gray-200-pale,.gray-300-pale,.gray-400-pale,.gray-50-pale,.gray-500-pale,.gray-600-pale,.gray-700-pale,.gray-800-pale,.gray-900-pale,.gray-950-pale,.gray-pale,.important-pale,.pale,.primary-pale,.secondary-pale,.special-pale,.success-pale,.warning-pale{--skin-color:rgba(var(--skin-pale-rgb),.1);--skin-text:rgba(var(--skin-pale-rgb),1);--state-color:rgba(var(--skin-pale-rgb),.1)}.pale{--skin-pale-rgb:var(--color-gray-500-rgb)}.primary-pale{--skin-pale-rgb:var(--color-primary-500-rgb)}.secondary-pale{--skin-pale-rgb:var(--color-secondary-500-rgb)}.success-pale{--skin-pale-rgb:var(--color-success-500-rgb)}.warning-pale{--skin-pale-rgb:var(--color-warning-500-rgb)}.danger-pale{--skin-pale-rgb:var(--color-danger-500-rgb)}.important-pale{--skin-pale-rgb:var(--color-important-500-rgb)}.special-pale{--skin-pale-rgb:var(--color-special-500-rgb)}.gray-50-pale{--skin-pale-rgb:var(--color-gray-50-rgb);--skin-text:var(--color-gray-400)}.gray-100-pale{--skin-pale-rgb:var(--color-gray-100-rgb);--skin-text:var(--color-gray-400)}.gray-200-pale{--skin-pale-rgb:var(--color-gray-200-rgb);--skin-text:var(--color-gray-400)}.gray-300-pale{--skin-pale-rgb:var(--color-gray-300-rgb);--skin-text:var(--color-gray-500)}.gray-400-pale{--skin-pale-rgb:var(--color-gray-400-rgb);--skin-text:var(--color-gray-500)}.gray-500-pale,.gray-pale{--skin-pale-rgb:var(--color-gray-500-rgb)}.gray-600-pale{--skin-pale-rgb:var(--color-gray-600-rgb)}.gray-700-pale{--skin-pale-rgb:var(--color-gray-700-rgb)}.gray-800-pale{--skin-pale-rgb:var(--color-gray-800-rgb)}.gray-900-pale{--skin-pale-rgb:var(--color-gray-900-rgb)}.gray-950-pale{--skin-pale-rgb:var(--color-gray-950-rgb)}.danger-outline,.dark-outline,.gray-300-outline,.gray-400-outline,.gray-600-outline,.gray-outline,.important-outline,.light-outline,.outline,.primary-outline,.secondary-outline,.special-outline,.success-outline,.warning-outline{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-outline:hover,.dark-outline:hover,.gray-300-outline:hover,.gray-400-outline:hover,.gray-600-outline:hover,.gray-outline:hover,.important-outline:hover,.light-outline:hover,.outline:hover,.primary-outline:hover,.secondary-outline:hover,.special-outline:hover,.success-outline:hover,.warning-outline:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-outline,.dark-outline,.gray-300-outline,.gray-400-outline,.gray-600-outline,.gray-outline,.important-outline,.light-outline,.outline,.primary-outline,.secondary-outline,.special-outline,.success-outline,.warning-outline{--skin-text:var(--skin-color,inherit);--skin-bg:transparent;--skin-color:rgba(var(--skin-outline-rgb),1);--state-color:rgba(var(--skin-outline-rgb),.1)}.outline{--skin-outline-rgb:var(--color-fore-rgb)}.primary-outline{--skin-outline-rgb:var(--color-primary-500-rgb)}.secondary-outline{--skin-outline-rgb:var(--color-secondary-500-rgb)}.success-outline{--skin-outline-rgb:var(--color-success-500-rgb)}.warning-outline{--skin-outline-rgb:var(--color-warning-500-rgb)}.danger-outline{--skin-outline-rgb:var(--color-danger-500-rgb)}.important-outline{--skin-outline-rgb:var(--color-important-500-rgb)}.special-outline{--skin-outline-rgb:var(--color-special-500-rgb)}.gray-300-outline{--skin-text:var(--color-gray-500);--skin-outline-rgb:var(--color-gray-300-rgb)}.gray-400-outline{--skin-text:var(--color-gray-500);--skin-outline-rgb:var(--color-gray-400-rgb)}.gray-outline{--skin-outline-rgb:var(--color-gray-500-rgb)}.gray-600-outline{--skin-outline-rgb:var(--color-gray-600-rgb)}.dark-outline{--skin-outline-rgb:var(--color-inverse-rgb)}.light-outline{--skin-outline-rgb:var(--color-canvas-rgb)}.danger-ghost,.ghost,.important-ghost,.primary-ghost,.secondary-ghost,.special-ghost,.success-ghost,.warning-ghost{--skin-bg:var(--skin-color);--skin-ring:var(--skin-color);--skin-border:var(--skin-color);--skin-hover-text:var(--skin-text);--skin-hover-bg:var(--skin-bg);--tw-ring-color:var(--skin-ring);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);--color-link-hover:var(--skin-text);background-color:var(--skin-bg);border-color:var(--skin-border);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);color:var(--skin-text)}.danger-ghost:hover,.ghost:hover,.important-ghost:hover,.primary-ghost:hover,.secondary-ghost:hover,.special-ghost:hover,.success-ghost:hover,.warning-ghost:hover{background-color:var(--skin-hover-bg);color:var(--skin-hover-text)}.danger-ghost,.ghost,.important-ghost,.primary-ghost,.secondary-ghost,.special-ghost,.success-ghost,.warning-ghost{--tw-ring-opacity:0;--tw-bg-opacity:0;--skin-text:var(--skin-color,inherit);--skin-bg:transparent;--skin-ring:transparent;--skin-color:rgba(var(--skin-ghost-rgb),1);--state-color:rgba(var(--skin-ghost-rgb),.1)}.ghost{--skin-ghost-rgb:var(--color-fore-rgb);--skin-text:inherit}.primary-ghost{--skin-ghost-rgb:var(--color-primary-500-rgb)}.secondary-ghost{--skin-ghost-rgb:var(--color-secondary-500-rgb)}.success-ghost{--skin-ghost-rgb:var(--color-success-500-rgb)}.warning-ghost{--skin-ghost-rgb:var(--color-warning-500-rgb)}.danger-ghost{--skin-ghost-rgb:var(--color-danger-500-rgb)}.important-ghost{--skin-ghost-rgb:var(--color-important-500-rgb)}.special-ghost{--skin-ghost-rgb:var(--color-special-500-rgb)}.font-sans{font-family:-apple-system,Noto Sans,Helvetica Neue,Helvetica,Nimbus Sans L,Arial,Liberation Sans,PingFang SC,Hiragino Sans GB,Noto Sans CJK SC,Source Han Sans SC,Source Han Sans CN,Microsoft YaHei,Wenquanyi Micro Hei,WenQuanYi Zen Hei,ST Heiti,SimHei,WenQuanYi Zen Hei Sharp,sans-serif}.font-serif{font-family:Nimbus Roman No9 L,Songti SC,Noto Serif CJK SC,Source Han Serif SC,Source Han Serif CN,STSong,AR PL New Sung,AR PL SungtiL GB,NSimSun,SimSun,TW-Sung,WenQuanYi Bitmap Song,AR PL UMing CN,AR PL UMing HK,AR PL UMing TW,AR PL UMing TW MBE,PMingLiU,MingLiU,serif}.font-mono{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace}.text-root{font-size:16px}.text-sm{font-size:.75rem;line-height:1rem}.text-base{font-size:.8125rem;line-height:1.25rem}.text-md{font-size:.875rem;line-height:1.3rem}.text-lg{font-size:1rem;line-height:1.5rem}.text-xl{font-size:1.125rem;line-height:1.75rem}.text-2xl{font-size:1.5rem;line-height:2rem}.text-3xl{font-size:1.875rem;line-height:2.25rem}.text-4xl{font-size:2.25rem;line-height:2.5rem}.font-thin{font-weight:100}.font-light{font-weight:300}.font-normal{font-weight:400}.font-medium{font-weight:500}.font-semibold{font-weight:600}.font-bold{font-weight:700}.font-black{font-weight:900}.leading-3{line-height:.75rem}.leading-4{line-height:1rem}.leading-5{line-height:1.25rem}.leading-6{line-height:1.5rem}.leading-7{line-height:1.75rem}.leading-8{line-height:2rem}.leading-9{line-height:2.25rem}.leading-10{line-height:2.5rem}.leading-none{line-height:1}.leading-tight{line-height:1.25}.leading-snug{line-height:1.375}.leading-normal{line-height:1.5}.leading-relaxed{line-height:1.625}.leading-loose{line-height:2}.line-clamp-1{-webkit-line-clamp:1}.line-clamp-1,.line-clamp-2{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-2{-webkit-line-clamp:2}.line-clamp-3{-webkit-line-clamp:3}.line-clamp-3,.line-clamp-4{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-4{-webkit-line-clamp:4}.line-clamp-5{-webkit-line-clamp:5}.line-clamp-5,.line-clamp-6{display:-webkit-box;overflow:hidden;-webkit-box-orient:vertical}.line-clamp-6{-webkit-line-clamp:6}.text-left{text-align:left}.text-center{text-align:center}.text-right{text-align:right}.text-justify{text-align:justify}.align-middle{vertical-align:middle}.align-top{vertical-align:top}.align-bottom{vertical-align:bottom}.align-sub{vertical-align:sub}.align-super{vertical-align:super}.text-primary{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.text-secondary{--tw-text-opacity:1;color:rgba(var(--color-secondary-500-rgb),var(--tw-text-opacity))}.text-success{--tw-text-opacity:1;color:rgba(var(--color-success-500-rgb),var(--tw-text-opacity))}.text-warning{--tw-text-opacity:1;color:rgba(var(--color-warning-500-rgb),var(--tw-text-opacity))}.text-danger{--tw-text-opacity:1;color:rgba(var(--color-danger-500-rgb),var(--tw-text-opacity))}.text-important{--tw-text-opacity:1;color:rgba(var(--color-important-500-rgb),var(--tw-text-opacity))}.text-special{--tw-text-opacity:1;color:rgba(var(--color-special-500-rgb),var(--tw-text-opacity))}.text-primary-50{--tw-text-opacity:1;color:rgba(var(--color-primary-50-rgb),var(--tw-text-opacity))}.text-primary-100{--tw-text-opacity:1;color:rgba(var(--color-primary-100-rgb),var(--tw-text-opacity))}.text-primary-200{--tw-text-opacity:1;color:rgba(var(--color-primary-200-rgb),var(--tw-text-opacity))}.text-primary-300{--tw-text-opacity:1;color:rgba(var(--color-primary-300-rgb),var(--tw-text-opacity))}.text-primary-400{--tw-text-opacity:1;color:rgba(var(--color-primary-400-rgb),var(--tw-text-opacity))}.text-primary-500{--tw-text-opacity:1;color:rgba(var(--color-primary-500-rgb),var(--tw-text-opacity))}.text-primary-600{--tw-text-opacity:1;color:rgba(var(--color-primary-600-rgb),var(--tw-text-opacity))}.text-primary-700{--tw-text-opacity:1;color:rgba(var(--color-primary-700-rgb),var(--tw-text-opacity))}.text-primary-800{--tw-text-opacity:1;color:rgba(var(--color-primary-800-rgb),var(--tw-text-opacity))}.text-primary-900{--tw-text-opacity:1;color:rgba(var(--color-primary-900-rgb),var(--tw-text-opacity))}.text-primary-950{--tw-text-opacity:1;color:rgba(var(--color-primary-950-rgb),var(--tw-text-opacity))}.text-secondary-50{--tw-text-opacity:1;color:rgba(var(--color-secondary-50-rgb),var(--tw-text-opacity))}.text-secondary-100{--tw-text-opacity:1;color:rgba(var(--color-secondary-100-rgb),var(--tw-text-opacity))}.text-secondary-200{--tw-text-opacity:1;color:rgba(var(--color-secondary-200-rgb),var(--tw-text-opacity))}.text-secondary-300{--tw-text-opacity:1;color:rgba(var(--color-secondary-300-rgb),var(--tw-text-opacity))}.text-secondary-400{--tw-text-opacity:1;color:rgba(var(--color-secondary-400-rgb),var(--tw-text-opacity))}.text-secondary-500{--tw-text-opacity:1;color:rgba(var(--color-secondary-500-rgb),var(--tw-text-opacity))}.text-secondary-600{--tw-text-opacity:1;color:rgba(var(--color-secondary-600-rgb),var(--tw-text-opacity))}.text-secondary-700{--tw-text-opacity:1;color:rgba(var(--color-secondary-700-rgb),var(--tw-text-opacity))}.text-secondary-800{--tw-text-opacity:1;color:rgba(var(--color-secondary-800-rgb),var(--tw-text-opacity))}.text-secondary-900{--tw-text-opacity:1;color:rgba(var(--color-secondary-900-rgb),var(--tw-text-opacity))}.text-secondary-950{--tw-text-opacity:1;color:rgba(var(--color-secondary-950-rgb),var(--tw-text-opacity))}.text-gray-50{--tw-text-opacity:1;color:rgba(var(--color-gray-50-rgb),var(--tw-text-opacity))}.text-gray-100{--tw-text-opacity:1;color:rgba(var(--color-gray-100-rgb),var(--tw-text-opacity))}.text-gray-200,.text-lightest{--tw-text-opacity:1;color:rgba(var(--color-gray-200-rgb),var(--tw-text-opacity))}.text-gray-300,.text-lighter{--tw-text-opacity:1;color:rgba(var(--color-gray-300-rgb),var(--tw-text-opacity))}.text-gray-400,.text-lighten{--tw-text-opacity:1;color:rgba(var(--color-gray-400-rgb),var(--tw-text-opacity))}.text-gray,.text-gray-500{--tw-text-opacity:1;color:rgba(var(--color-gray-500-rgb),var(--tw-text-opacity))}.text-darken,.text-gray-600{--tw-text-opacity:1;color:rgba(var(--color-gray-600-rgb),var(--tw-text-opacity))}.text-darker,.text-gray-700{--tw-text-opacity:1;color:rgba(var(--color-gray-700-rgb),var(--tw-text-opacity))}.text-darkest,.text-gray-800{--tw-text-opacity:1;color:rgba(var(--color-gray-800-rgb),var(--tw-text-opacity))}.text-gray-900{--tw-text-opacity:1;color:rgba(var(--color-gray-900-rgb),var(--tw-text-opacity))}.text-gray-950{--tw-text-opacity:1;color:rgba(var(--color-gray-950-rgb),var(--tw-text-opacity))}.text-white{--tw-text-opacity:1;color:rgba(var(--color-white-rgb),var(--tw-text-opacity))}.text-black{--tw-text-opacity:1;color:rgba(var(--color-black-rgb),var(--tw-text-opacity))}.text-transparent{color:transparent}.text-canvas{--tw-text-opacity:1;color:rgba(var(--color-canvas-rgb),var(--tw-text-opacity))}.text-surface-light{--tw-text-opacity:1;color:rgba(var(--color-surface-light-rgb),var(--tw-text-opacity))}.text-surface{--tw-text-opacity:1;color:rgba(var(--color-surface-rgb),var(--tw-text-opacity))}.text-surface-strong{--tw-text-opacity:1;color:rgba(var(--color-surface-strong-rgb),var(--tw-text-opacity))}.text-inverse{--tw-text-opacity:1;color:rgba(var(--color-inverse-rgb),var(--tw-text-opacity))}.text-fore-in-light{--tw-text-opacity:1;color:rgba(var(--color-fore-in-light-rgb),var(--tw-text-opacity))}.text-fore-in-dark{--tw-text-opacity:1;color:rgba(var(--color-fore-in-dark-rgb),var(--tw-text-opacity))}.text-fore{--tw-text-opacity:1;color:rgba(var(--color-fore-rgb),var(--tw-text-opacity))}.text-focus{--tw-text-opacity:1;color:rgba(var(--color-focus-rgb),var(--tw-text-opacity))}.text-link{--tw-text-opacity:1;color:rgba(var(--color-link-rgb),var(--tw-text-opacity))}.text-link-hover{--tw-text-opacity:1;color:rgba(var(--color-link-hover-rgb),var(--tw-text-opacity))}.text-current{color:currentColor}.text-inherit{color:inherit}.clip,.ellipsis,.text-clip,.text-ellipsis{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.clip,.text-clip{text-overflow:clip}.whitespace-normal{white-space:normal}.nowrap,.whitespace-nowrap{white-space:nowrap}.pre,.whitespace-pre{white-space:pre}.pre-line,.whitespace-pre-line{white-space:pre-line}.pre-wrap,.whitespace-pre-wrap{white-space:pre-wrap}.break-normal{overflow-wrap:normal;word-break:normal}.break-words{overflow-wrap:break-word}.break-all{word-break:break-all}.text-opacity-0{--tw-text-opacity:0}.text-opacity-5{--tw-text-opacity:.05}.text-opacity-10{--tw-text-opacity:.1}.text-opacity-20{--tw-text-opacity:.2}.text-opacity-25{--tw-text-opacity:.25}.text-opacity-30{--tw-text-opacity:.3}.text-opacity-40{--tw-text-opacity:.4}.text-opacity-50{--tw-text-opacity:.5}.text-opacity-60{--tw-text-opacity:.6}.text-opacity-70{--tw-text-opacity:.7}.text-opacity-80{--tw-text-opacity:.8}.text-opacity-90{--tw-text-opacity:.9}.text-opacity-95{--tw-text-opacity:.95}.text-opacity-100{--tw-text-opacity:1}.uppercase{text-transform:uppercase}.lowercase{text-transform:lowercase}.capitalize{text-transform:capitalize}.normal-case{text-transform:none}.list-none{list-style-type:none}.list-disc{list-style-type:disc}.list-decimal{list-style-type:decimal}.list-unstyled{list-style-type:none;padding-left:0}.underline{text-decoration-line:underline}.overline{text-decoration-line:overline}.line-through{text-decoration-line:line-through}.no-underline{text-decoration-line:none}.bg-primary{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity))}.bg-secondary{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-500-rgb),var(--tw-bg-opacity))}.bg-success{--tw-bg-opacity:1;background-color:rgba(var(--color-success-500-rgb),var(--tw-bg-opacity))}.bg-warning{--tw-bg-opacity:1;background-color:rgba(var(--color-warning-500-rgb),var(--tw-bg-opacity))}.bg-danger{--tw-bg-opacity:1;background-color:rgba(var(--color-danger-500-rgb),var(--tw-bg-opacity))}.bg-important{--tw-bg-opacity:1;background-color:rgba(var(--color-important-500-rgb),var(--tw-bg-opacity))}.bg-special{--tw-bg-opacity:1;background-color:rgba(var(--color-special-500-rgb),var(--tw-bg-opacity))}.bg-primary-50{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-50-rgb),var(--tw-bg-opacity))}.bg-primary-100{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-100-rgb),var(--tw-bg-opacity))}.bg-primary-200{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-200-rgb),var(--tw-bg-opacity))}.bg-primary-300{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-300-rgb),var(--tw-bg-opacity))}.bg-primary-400{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-400-rgb),var(--tw-bg-opacity))}.bg-primary-500{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-500-rgb),var(--tw-bg-opacity))}.bg-primary-600{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-600-rgb),var(--tw-bg-opacity))}.bg-primary-700{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-700-rgb),var(--tw-bg-opacity))}.bg-primary-800{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-800-rgb),var(--tw-bg-opacity))}.bg-primary-900{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-900-rgb),var(--tw-bg-opacity))}.bg-primary-950{--tw-bg-opacity:1;background-color:rgba(var(--color-primary-950-rgb),var(--tw-bg-opacity))}.bg-secondary-50{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-50-rgb),var(--tw-bg-opacity))}.bg-secondary-100{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-100-rgb),var(--tw-bg-opacity))}.bg-secondary-200{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-200-rgb),var(--tw-bg-opacity))}.bg-secondary-300{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-300-rgb),var(--tw-bg-opacity))}.bg-secondary-400{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-400-rgb),var(--tw-bg-opacity))}.bg-secondary-500{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-500-rgb),var(--tw-bg-opacity))}.bg-secondary-600{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-600-rgb),var(--tw-bg-opacity))}.bg-secondary-700{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-700-rgb),var(--tw-bg-opacity))}.bg-secondary-800{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-800-rgb),var(--tw-bg-opacity))}.bg-secondary-900{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-900-rgb),var(--tw-bg-opacity))}.bg-secondary-950{--tw-bg-opacity:1;background-color:rgba(var(--color-secondary-950-rgb),var(--tw-bg-opacity))}.bg-gray-50{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-50-rgb),var(--tw-bg-opacity))}.bg-gray-100{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-100-rgb),var(--tw-bg-opacity))}.bg-gray-200,.bg-lightest{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-200-rgb),var(--tw-bg-opacity))}.bg-gray-300,.bg-lighter{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-300-rgb),var(--tw-bg-opacity))}.bg-gray-400,.bg-light{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-400-rgb),var(--tw-bg-opacity))}.bg-gray,.bg-gray-500{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-500-rgb),var(--tw-bg-opacity))}.bg-darken,.bg-gray-600{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-600-rgb),var(--tw-bg-opacity))}.bg-darker,.bg-gray-700{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-700-rgb),var(--tw-bg-opacity))}.bg-darkest,.bg-gray-800{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-800-rgb),var(--tw-bg-opacity))}.bg-gray-900{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-900-rgb),var(--tw-bg-opacity))}.bg-gray-950{--tw-bg-opacity:1;background-color:rgba(var(--color-gray-950-rgb),var(--tw-bg-opacity))}.bg-canvas{--tw-bg-opacity:1;background-color:rgba(var(--color-canvas-rgb),var(--tw-bg-opacity))}.bg-surface-light{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-light-rgb),var(--tw-bg-opacity))}.bg-surface{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-rgb),var(--tw-bg-opacity))}.bg-surface-strong{--tw-bg-opacity:1;background-color:rgba(var(--color-surface-strong-rgb),var(--tw-bg-opacity))}.bg-inverse{--tw-bg-opacity:1;background-color:rgba(var(--color-inverse-rgb),var(--tw-bg-opacity))}.bg-fore-in-light{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-in-light-rgb),var(--tw-bg-opacity))}.bg-fore-in-dark{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-in-dark-rgb),var(--tw-bg-opacity))}.bg-fore{--tw-bg-opacity:1;background-color:rgba(var(--color-fore-rgb),var(--tw-bg-opacity))}.bg-focus{--tw-bg-opacity:1;background-color:rgba(var(--color-focus-rgb),var(--tw-bg-opacity))}.bg-white{--tw-bg-opacity:1;background-color:rgba(var(--color-white-rgb),var(--tw-bg-opacity))}.bg-black{--tw-bg-opacity:1;background-color:rgba(var(--color-black-rgb),var(--tw-bg-opacity))}.bg-transparent{background-color:transparent}.bg-current{background-color:currentColor}.bg-inherit{background-color:inherit}.bg-none{background-image:none}.bg-opacity-0{--tw-bg-opacity:0}.bg-opacity-5{--tw-bg-opacity:.05}.bg-opacity-10{--tw-bg-opacity:.1}.bg-opacity-20{--tw-bg-opacity:.2}.bg-opacity-25{--tw-bg-opacity:.25}.bg-opacity-30{--tw-bg-opacity:.3}.bg-opacity-40{--tw-bg-opacity:.4}.bg-opacity-50{--tw-bg-opacity:.5}.bg-opacity-60{--tw-bg-opacity:.6}.bg-opacity-70{--tw-bg-opacity:.7}.bg-opacity-80{--tw-bg-opacity:.8}.bg-opacity-90{--tw-bg-opacity:.9}.bg-opacity-100{--tw-bg-opacity:1}.bg-auto{background-size:auto}.bg-cover{background-size:cover}.bg-contain{background-size:contain}.bg-repeat{background-repeat:repeat}.bg-no-repeat{background-repeat:no-repeat}.bg-repeat-x{background-repeat:repeat-x}.bg-repeat-y{background-repeat:repeat-y}.bg-repeat-round{background-repeat:round}.bg-repeat-space{background-repeat:space}.bg-bottom{background-position:bottom}.bg-center{background-position:50%}.bg-left{background-position:0}.bg-left-bottom{background-position:0 100%}.bg-left-top{background-position:0 0}.bg-right{background-position:100%}.bg-right-bottom{background-position:100% 100%}.bg-right-top{background-position:100% 0}.bg-top{background-position:top}.bg-fixed{background-attachment:fixed}.bg-local{background-attachment:local}.bg-scroll{background-attachment:scroll}.divider{align-self:stretch;border-color:currentColor;border-left-width:1px;border-top-width:1px;opacity:.1}.border-0{border-width:0}.border{border-width:1px}.border-2{border-width:2px}.border-4{border-width:4px}.border-t{border-top-width:1px}.border-l{border-left-width:1px}.border-r{border-right-width:1px}.border-b{border-bottom-width:1px}.border-t-0{border-top-width:0}.border-r-0{border-right-width:0}.border-b-0{border-bottom-width:0}.border-l-0{border-left-width:0}.border-t-2{border-top-width:2px}.border-l-2{border-left-width:2px}.border-r-2{border-right-width:2px}.border-b-2{border-bottom-width:2px}.border-t-4{border-top-width:4px}.border-l-4{border-left-width:4px}.border-r-4{border-right-width:4px}.border-b-4{border-bottom-width:4px}.border-light{--tw-border-opacity:1;border-color:rgba(var(--color-border-light-rgb),var(--tw-border-opacity))}.border-strong{--tw-border-opacity:1;border-color:rgba(var(--color-border-strong-rgb),var(--tw-border-opacity))}.border-primary{--tw-border-opacity:1;border-color:rgba(var(--color-primary-500-rgb),var(--tw-border-opacity))}.border-secondary{--tw-border-opacity:1;border-color:rgba(var(--color-secondary-500-rgb),var(--tw-border-opacity))}.border-success{--tw-border-opacity:1;border-color:rgba(var(--color-success-500-rgb),var(--tw-border-opacity))}.border-warning{--tw-border-opacity:1;border-color:rgba(var(--color-warning-500-rgb),var(--tw-border-opacity))}.border-danger{--tw-border-opacity:1;border-color:rgba(var(--color-danger-500-rgb),var(--tw-border-opacity))}.border-important{--tw-border-opacity:1;border-color:rgba(var(--color-important-500-rgb),var(--tw-border-opacity))}.border-special{--tw-border-opacity:1;border-color:rgba(var(--color-special-500-rgb),var(--tw-border-opacity))}.border-gray-50{--tw-border-opacity:1;border-color:rgba(var(--color-gray-50-rgb),var(--tw-border-opacity))}.border-gray-100{--tw-border-opacity:1;border-color:rgba(var(--color-gray-100-rgb),var(--tw-border-opacity))}.border-gray-200{--tw-border-opacity:1;border-color:rgba(var(--color-gray-200-rgb),var(--tw-border-opacity))}.border-gray-300{--tw-border-opacity:1;border-color:rgba(var(--color-gray-300-rgb),var(--tw-border-opacity))}.border-gray-400{--tw-border-opacity:1;border-color:rgba(var(--color-gray-400-rgb),var(--tw-border-opacity))}.border-gray,.border-gray-500{--tw-border-opacity:1;border-color:rgba(var(--color-gray-500-rgb),var(--tw-border-opacity))}.border-gray-600{--tw-border-opacity:1;border-color:rgba(var(--color-gray-600-rgb),var(--tw-border-opacity))}.border-gray-700{--tw-border-opacity:1;border-color:rgba(var(--color-gray-700-rgb),var(--tw-border-opacity))}.border-gray-800{--tw-border-opacity:1;border-color:rgba(var(--color-gray-800-rgb),var(--tw-border-opacity))}.border-gray-900{--tw-border-opacity:1;border-color:rgba(var(--color-gray-900-rgb),var(--tw-border-opacity))}.border-gray-950{--tw-border-opacity:1;border-color:rgba(var(--color-gray-950-rgb),var(--tw-border-opacity))}.border-white{--tw-border-opacity:1;border-color:rgba(var(--color-white-rgb),var(--tw-border-opacity))}.border-black{--tw-border-opacity:1;border-color:rgba(var(--color-black-rgb),var(--tw-border-opacity))}.border-canvas{--tw-border-opacity:1;border-color:rgba(var(--color-canvas-rgb),var(--tw-border-opacity))}.border-surface-light{--tw-border-opacity:1;border-color:rgba(var(--color-surface-light-rgb),var(--tw-border-opacity))}.border-surface{--tw-border-opacity:1;border-color:rgba(var(--color-surface-rgb),var(--tw-border-opacity))}.border-surface-strong{--tw-border-opacity:1;border-color:rgba(var(--color-surface-strong-rgb),var(--tw-border-opacity))}.border-inverse{--tw-border-opacity:1;border-color:rgba(var(--color-inverse-rgb),var(--tw-border-opacity))}.border-fore-in-light{--tw-border-opacity:1;border-color:rgba(var(--color-fore-in-light-rgb),var(--tw-border-opacity))}.border-fore-in-dark{--tw-border-opacity:1;border-color:rgba(var(--color-fore-in-dark-rgb),var(--tw-border-opacity))}.border-fore{--tw-border-opacity:1;border-color:rgba(var(--color-fore-rgb),var(--tw-border-opacity))}.border-focus{--tw-border-opacity:1;border-color:rgba(var(--color-focus-rgb),var(--tw-border-opacity))}.border-link{--tw-border-opacity:1;border-color:rgba(var(--color-link-rgb),var(--tw-border-opacity))}.border-link-hover{--tw-border-opacity:1;border-color:rgba(var(--color-link-hover-rgb),var(--tw-border-opacity))}.border-transparent{border-color:transparent}.border-current{border-color:currentColor}.border-inherit{border-color:inherit}.border-solid{border-style:solid}.border-dashed{border-style:dashed}.border-dotted{border-style:dotted}.border-double{border-style:double}.border-hidden{border-style:hidden}.border-none{border-style:none}.border-opacity-0{--tw-border-opacity:0}.border-opacity-5{--tw-border-opacity:.05}.border-opacity-10{--tw-border-opacity:.1}.border-opacity-20{--tw-border-opacity:.2}.border-opacity-25{--tw-border-opacity:.25}.border-opacity-30{--tw-border-opacity:.3}.border-opacity-40{--tw-border-opacity:.4}.border-opacity-50{--tw-border-opacity:.5}.border-opacity-60{--tw-border-opacity:.6}.border-opacity-70{--tw-border-opacity:.7}.border-opacity-80{--tw-border-opacity:.8}.border-opacity-90{--tw-border-opacity:.9}.border-opacity-95{--tw-border-opacity:.95}.border-opacity-100{--tw-border-opacity:1}.rounded-none{border-radius:var(--radius-none)}.rounded-sm{border-radius:var(--radius-sm)}.rounded{border-radius:var(--radius)}.rounded-md{border-radius:var(--radius-md)}.rounded-lg{border-radius:var(--radius-lg)}.rounded-xl{border-radius:var(--radius-xl)}.rounded-2xl{border-radius:var(--radius-2xl)}.rounded-3xl{border-radius:var(--radius-3xl)}.circle,.rounded-full{border-radius:var(--radius-full)}.rounded-l-none{border-bottom-left-radius:var(--radius-none);border-top-left-radius:var(--radius-none)}.rounded-t-none{border-top-left-radius:var(--radius-none)}.rounded-r-none,.rounded-t-none{border-top-right-radius:var(--radius-none)}.rounded-b-none,.rounded-r-none{border-bottom-right-radius:var(--radius-none)}.rounded-b-none{border-bottom-left-radius:var(--radius-none)}.rounded-br-none{border-bottom-right-radius:var(--radius-none)}.rounded-bl-none{border-bottom-left-radius:var(--radius-none)}.rounded-tr-none{border-top-right-radius:var(--radius-none)}.rounded-tl-none{border-top-left-radius:var(--radius-none)}.ring{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(1px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000);--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.ring-border-light{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-light-rgb),var(--tw-ring-opacity))}.ring-border{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-rgb),var(--tw-ring-opacity))}.ring-border-strong{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-border-strong-rgb),var(--tw-ring-opacity))}.ring-light{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.05}.ring-gray{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.1}.ring-dark{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.2}.ring-darker{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.3}.ring-darkest{--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity));--tw-ring-opacity:0.5}.ring-primary{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-primary-500-rgb),var(--tw-ring-opacity))}.ring-secondary{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-secondary-500-rgb),var(--tw-ring-opacity))}.ring-warning{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-warning-500-rgb),var(--tw-ring-opacity))}.ring-success{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-success-500-rgb),var(--tw-ring-opacity))}.ring-danger{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-danger-500-rgb),var(--tw-ring-opacity))}.ring-important{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-important-500-rgb),var(--tw-ring-opacity))}.ring-special{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-special-500-rgb),var(--tw-ring-opacity))}.ring-gray-50{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-50-rgb),var(--tw-ring-opacity))}.ring-gray-100{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-100-rgb),var(--tw-ring-opacity))}.ring-gray-200{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-200-rgb),var(--tw-ring-opacity))}.ring-gray-300{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-300-rgb),var(--tw-ring-opacity))}.ring-gray-400{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-400-rgb),var(--tw-ring-opacity))}.ring-gray-500{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-500-rgb),var(--tw-ring-opacity))}.ring-gray-600{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-600-rgb),var(--tw-ring-opacity))}.ring-gray-700{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-700-rgb),var(--tw-ring-opacity))}.ring-gray-800{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-800-rgb),var(--tw-ring-opacity))}.ring-gray-900{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-900-rgb),var(--tw-ring-opacity))}.ring-gray-950{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-gray-950-rgb),var(--tw-ring-opacity))}.ring-inverse{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-inverse-rgb),var(--tw-ring-opacity))}.ring-canvas{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-canvas-rgb),var(--tw-ring-opacity))}.ring-surface{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-surface-rgb),var(--tw-ring-opacity))}.ring-fore{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-fore-rgb),var(--tw-ring-opacity))}.ring-transparent{--tw-ring-color:transparent}.ring-black{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-black-rgb),var(--tw-ring-opacity))}.ring-white{--tw-ring-opacity:1;--tw-ring-color:rgba(var(--color-white-rgb),var(--tw-ring-opacity))}.ring-inherit{--tw-ring-color:inherit}.ring-current{--tw-ring-color:currentColor}.ring-opacity-0{--tw-ring-opacity:0}.ring-opacity-5{--tw-ring-opacity:.05}.ring-opacity-10{--tw-ring-opacity:.1}.ring-opacity-20{--tw-ring-opacity:.2}.ring-opacity-30{--tw-ring-opacity:.3}.ring-opacity-40{--tw-ring-opacity:.4}.ring-opacity-50{--tw-ring-opacity:.5}.ring-opacity-60{--tw-ring-opacity:.6}.ring-opacity-70{--tw-ring-opacity:.7}.ring-opacity-80{--tw-ring-opacity:.8}.ring-opacity-90{--tw-ring-opacity:.9}.ring-opacity-100{--tw-ring-opacity:1}.ring-0{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-0,.ring-2{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-2{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-3{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-3,.ring-4{box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-4{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(4px + var(--tw-ring-offset-width)) var(--tw-ring-color)}.ring-8{--tw-ring-offset-shadow:var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);--tw-ring-shadow:var(--tw-ring-inset) 0 0 0 calc(8px + var(--tw-ring-offset-width)) var(--tw-ring-color);box-shadow:var(--tw-ring-offset-shadow),var(--tw-ring-shadow),var(--tw-shadow,0 0 #0000)}.ring-inset{--tw-ring-inset:inset}.ring-offset-0{--tw-ring-offset-width:0px}.ring-offset-1{--tw-ring-offset-width:1px}.ring-offset-2{--tw-ring-offset-width:2px}.ring-offset-4{--tw-ring-offset-width:4px}.ring-offset-8{--tw-ring-offset-width:8px}.shadow-sm{--tw-shadow:0 1px 2px 0 rgba(0,0,0,.04),0 0 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 1px 2px 0 var(--tw-shadow-color),0 0 2px -1px var(--tw-shadow-color)}.shadow,.shadow-sm{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow{--tw-shadow:0 3px 8px 0 rgba(0,0,0,.04),0 1px 2px -1px rgba(0,0,0,.01);--tw-shadow-colored:0 3px 8px 0 var(--tw-shadow-color),0 1px 2px -1px var(--tw-shadow-color)}.shadow-md{--tw-shadow:0 2px 6px -1px rgba(0,0,0,.2),0 1px 4px -2px rgba(0,0,0,.15);--tw-shadow-colored:0 2px 6px -1px var(--tw-shadow-color),0 1px 4px -2px var(--tw-shadow-color)}.shadow-lg,.shadow-md{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-lg{--tw-shadow:0 5px 15px -3px rgba(0,0,0,.2),0 2px 6px -4px rgba(0,0,0,.15);--tw-shadow-colored:0 5px 15px -3px var(--tw-shadow-color),0 2px 6px -4px var(--tw-shadow-color)}.shadow-xl{--tw-shadow:0 10px 25px -5px rgba(0,0,0,.2),0 4px 10px -6px rgba(0,0,0,.15);--tw-shadow-colored:0 10px 25px -5px var(--tw-shadow-color),0 4px 10px -6px var(--tw-shadow-color)}.shadow-2xl,.shadow-xl{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-2xl{--tw-shadow:0 10px 50px -10px rgba(0,0,0,.4),0 8px 20px -10px rgba(0,0,0,.3);--tw-shadow-colored:0 10px 50px -10px var(--tw-shadow-color),0 8px 20px -10px var(--tw-shadow-color)}.shadow-inner{--tw-shadow:inset 0 2px 4px 0 rgba(0,0,0,.05);--tw-shadow-colored:inset 0 2px 4px 0 var(--tw-shadow-color)}.shadow-inner,.shadow-none{box-shadow:var(--tw-ring-offset-shadow,0 0 #0000),var(--tw-ring-shadow,0 0 #0000),var(--tw-shadow)}.shadow-none{--tw-shadow:0 0 #0000;--tw-shadow-colored:0 0 #0000}.muted{opacity:var(--opacity-muted)}.opacity-0{opacity:0}.opacity-5{opacity:.05}.opacity-10{opacity:.1}.opacity-20{opacity:.2}.opacity-25{opacity:.25}.opacity-30{opacity:.3}.opacity-40{opacity:.4}.opacity-50{opacity:.5}.opacity-60{opacity:.6}.opacity-70{opacity:.7}.opacity-75{opacity:.75}.opacity-80{opacity:.8}.opacity-90{opacity:.9}.opacity-95{opacity:.95}.opacity-100{opacity:1}.blur-none{--tw-blur:blur(0)}.blur-none,.blur-sm{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-sm{--tw-blur:blur(4px)}.blur{--tw-blur:blur(8px)}.blur,.blur-md{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-md{--tw-blur:blur(12px)}.blur-lg{--tw-blur:blur(16px)}.blur-lg,.blur-xl{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.blur-xl{--tw-blur:blur(24px)}.grayscale{--tw-grayscale:grayscale(100%)}.grayscale,.invert{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.invert{--tw-invert:invert(100%)}.filter-none{filter:none!important}.drop-shadow-none{--tw-drop-shadow:drop-shadow(0 0 #0000)}.drop-shadow-none,.drop-shadow-sm{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-sm{--tw-drop-shadow:drop-shadow(0 1px 1px rgba(0,0,0,.05))}.drop-shadow{--tw-drop-shadow:drop-shadow(0 1px 2px rgba(0,0,0,.1)) drop-shadow(0 1px 1px rgba(0,0,0,.06))}.drop-shadow,.drop-shadow-md{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-md{--tw-drop-shadow:drop-shadow(0 4px 3px rgba(0,0,0,.07)) drop-shadow(0 2px 2px rgba(0,0,0,.06))}.drop-shadow-lg{--tw-drop-shadow:drop-shadow(0 10px 8px rgba(0,0,0,.04)) drop-shadow(0 4px 3px rgba(0,0,0,.1))}.drop-shadow-lg,.drop-shadow-xl{filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.drop-shadow-xl{--tw-drop-shadow:drop-shadow(0 20px 13px rgba(0,0,0,.03)) drop-shadow(0 8px 5px rgba(0,0,0,.08))}.drop-shadow-2xl{--tw-drop-shadow:drop-shadow(0 25px 25px rgba(0,0,0,.15));filter:var(--tw-blur) var(--tw-brightness) var(--tw-contrast) var(--tw-grayscale) var(--tw-hue-rotate) var(--tw-invert) var(--tw-saturate) var(--tw-sepia) var(--tw-drop-shadow)}.backdrop-blur-none{--tw-backdrop-blur:blur(0)}.backdrop-blur-none,.backdrop-blur-sm{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-sm{--tw-backdrop-blur:blur(4px)}.backdrop-blur{--tw-backdrop-blur:blur(8px)}.backdrop-blur,.backdrop-blur-md{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-md{--tw-backdrop-blur:blur(12px)}.backdrop-blur-lg{--tw-backdrop-blur:blur(16px)}.backdrop-blur-lg,.backdrop-blur-xl{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-xl{--tw-backdrop-blur:blur(24px)}.backdrop-blur-2xl{--tw-backdrop-blur:blur(40px)}.backdrop-blur-2xl,.backdrop-blur-3xl{-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.backdrop-blur-3xl{--tw-backdrop-blur:blur(64px)}.transition{transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,-webkit-backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke,opacity,box-shadow,transform,filter,backdrop-filter,-webkit-backdrop-filter;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-all{transition-duration:.15s;transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-colors{transition-duration:.15s;transition-property:color,background-color,border-color,text-decoration-color,fill,stroke;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-opacity{transition-duration:.15s;transition-property:opacity;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-shadow{transition-duration:.15s;transition-property:box-shadow;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-transform{transition-duration:.15s;transition-property:transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.transition-none{transition-property:none}.fade,.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{opacity:0;transition-duration:.15s;transition-property:opacity,transform;transition-timing-function:cubic-bezier(.4,0,.2,1)}.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{--tw-scale-x:.9;--tw-scale-y:.9}.fade-from-bottom,.fade-from-center,.fade-from-left,.fade-from-right,.fade-from-top{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-bottom{--tw-translate-y:25%}.fade-from-top{--tw-translate-y:-25%}.fade-from-left,.fade-from-top{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-left{--tw-translate-x:-25%}.fade-from-right{--tw-translate-x:25%}.fade-from-bottom.in,.fade-from-center.in,.fade-from-left.in,.fade-from-right,.fade-from-right.in,.fade-from-top.in,.fade.in{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.fade-from-bottom.in,.fade-from-center.in,.fade-from-left.in,.fade-from-right.in,.fade-from-top.in,.fade.in{--tw-translate-x:0px;--tw-translate-y:0px;--tw-scale-x:1;--tw-scale-y:1;opacity:1}.duration-75{transition-duration:75ms}.duration-100{transition-duration:.1s}.duration-200{transition-duration:.2s}.duration-300{transition-duration:.3s}.duration-500{transition-duration:.5s}.duration-1000{transition-duration:1s}@keyframes -spin{to{transform:rotate(1turn)}}.animate-spin,.spin{animation:-spin 1s linear infinite}@keyframes -ping{75%,to{opacity:0;transform:scale(2)}}.animate-ping,.ping{animation:-ping 1s cubic-bezier(0,0,.2,1) infinite}@keyframes -pulse{50%{opacity:.5}}.animate-pulse,.pulse{animation:-pulse 2s cubic-bezier(.4,0,.6,1) infinite}@keyframes -bounce{0%,to{animation-timing-function:cubic-bezier(.8,0,1,1);transform:translateY(-25%)}50%{animation-timing-function:cubic-bezier(0,0,.2,1);transform:none}}.animate-bounce,.bounce{animation:-bounce 1s infinite}.scale-0{--tw-scale-x:0;--tw-scale-y:0}.scale-0,.scale-50{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-50{--tw-scale-x:.5;--tw-scale-y:.5}.scale-75{--tw-scale-x:.75;--tw-scale-y:.75}.scale-75,.scale-90{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-90{--tw-scale-x:.9;--tw-scale-y:.9}.scale-95{--tw-scale-x:.95;--tw-scale-y:.95}.scale-100,.scale-95{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-100{--tw-scale-x:1;--tw-scale-y:1}.scale-105{--tw-scale-x:1.05;--tw-scale-y:1.05}.scale-105,.scale-110{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-110{--tw-scale-x:1.1;--tw-scale-y:1.1}.scale-125{--tw-scale-x:1.25;--tw-scale-y:1.25}.scale-125,.scale-150{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.scale-150{--tw-scale-x:1.5;--tw-scale-y:1.5}.flip-x{--tw-scale-x:-1}.flip-x,.flip-y{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.flip-y{--tw-scale-y:-1}.rotate-0{--tw-rotate:0deg}.rotate-0,.rotate-1{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-1{--tw-rotate:1deg}.rotate-2{--tw-rotate:2deg}.rotate-2,.rotate-3{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-3{--tw-rotate:3deg}.rotate-6{--tw-rotate:6deg}.rotate-12,.rotate-6{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-12{--tw-rotate:12deg}.rotate-45{--tw-rotate:45deg}.rotate-45,.rotate-90{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-90{--tw-rotate:90deg}.rotate-135{--tw-rotate:135deg}.rotate-135,.rotate-180{transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.rotate-180{--tw-rotate:180deg}.rotate-270{--tw-rotate:270deg;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skewX(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.basis-0{flex-basis:0px}.basis-1{flex-basis:0.25rem}.basis-2{flex-basis:0.5rem}.basis-3{flex-basis:0.75rem}.basis-4{flex-basis:1rem}.basis-5{flex-basis:1.25rem}.basis-6{flex-basis:1.5rem}.basis-7{flex-basis:1.75rem}.basis-8{flex-basis:2rem}.basis-9{flex-basis:2.25rem}.basis-10{flex-basis:2.5rem}.basis-11{flex-basis:2.75rem}.basis-12{flex-basis:3rem}.basis-14{flex-basis:3.5rem}.basis-16{flex-basis:4rem}.basis-20{flex-basis:5rem}.basis-24{flex-basis:6rem}.basis-28{flex-basis:7rem}.basis-32{flex-basis:8rem}.basis-36{flex-basis:9rem}.basis-40{flex-basis:10rem}.basis-44{flex-basis:11rem}.basis-48{flex-basis:12rem}.basis-52{flex-basis:13rem}.basis-56{flex-basis:14rem}.basis-60{flex-basis:15rem}.basis-64{flex-basis:16rem}.basis-72{flex-basis:18rem}.basis-80{flex-basis:20rem}.basis-96{flex-basis:24rem}.basis-auto{flex-basis:auto}.basis-px{flex-basis:1px}.basis-0\.5{flex-basis:0.125rem}.basis-1\.5{flex-basis:0.375rem}.basis-2\.5{flex-basis:0.625rem}.basis-3\.5{flex-basis:0.875rem}.basis-1\/2{flex-basis:50%}.basis-1\/3{flex-basis:33.333333%}.basis-2\/3{flex-basis:66.666667%}.basis-1\/4{flex-basis:25%}.basis-2\/4{flex-basis:50%}.basis-3\/4{flex-basis:75%}.basis-1\/5{flex-basis:20%}.basis-2\/5{flex-basis:40%}.basis-3\/5{flex-basis:60%}.basis-4\/5{flex-basis:80%}.basis-1\/6{flex-basis:16.666667%}.basis-2\/6{flex-basis:33.333333%}.basis-3\/6{flex-basis:50%}.basis-4\/6{flex-basis:66.666667%}.basis-5\/6{flex-basis:83.333333%}.basis-1\/12{flex-basis:8.333333%}.basis-2\/12{flex-basis:16.666667%}.basis-3\/12{flex-basis:25%}.basis-4\/12{flex-basis:33.333333%}.basis-5\/12{flex-basis:41.666667%}.basis-6\/12{flex-basis:50%}.basis-7\/12{flex-basis:58.333333%}.basis-8\/12{flex-basis:66.666667%}.basis-9\/12{flex-basis:75%}.basis-10\/12{flex-basis:83.333333%}.basis-11\/12{flex-basis:91.666667%}.basis-full{flex-basis:100%}.row{display:flex;flex-direction:row}.center,.col{display:flex;flex-direction:column}.center,.center-row{align-items:center;justify-content:center}.center-row{display:flex;flex-direction:row}.center-x,.center-y{align-items:center;display:flex}.center-y{flex-direction:column}.row-reverse{display:flex;flex-direction:row-reverse}.col-reverse{display:flex;flex-direction:column-reverse}.flex-wrap{flex-wrap:wrap}.flex-wrap-reverse{flex-wrap:wrap-reverse}.flex-nowrap{flex-wrap:nowrap}.flex-1{flex:1 1 0%}.flex-auto{flex:1 1 auto}.flex-initial{flex:0 1 auto}.flex-none{flex:none}.grow{flex-grow:1!important}.grow-0{flex-grow:0!important}.shrink{flex-shrink:1}.shrink-0{flex-shrink:0}.order-1{order:1}.order-2{order:2}.order-3{order:3}.order-4{order:4}.order-5{order:5}.order-6{order:6}.order-7{order:7}.order-8{order:8}.order-9{order:9}.order-10{order:10}.order-11{order:11}.order-12{order:12}.order-first{order:-9999}.order-last{order:9999}.order-none{order:0}.gap-0{gap:0}.gap-x-0{-moz-column-gap:0;column-gap:0}.gap-y-0{row-gap:0}.gap-px{gap:1px}.gap-x-px{-moz-column-gap:1px;column-gap:1px}.gap-y-px{row-gap:1px}.gap-0\.5{gap:.125rem}.gap-x-0\.5{-moz-column-gap:.125rem;column-gap:.125rem}.gap-y-0\.5{row-gap:.125rem}.gap-3px{gap:3px}.gap-1{gap:.25rem}.gap-x-1{-moz-column-gap:.25rem;column-gap:.25rem}.gap-y-1{row-gap:.25rem}.gap-1\.5{gap:.375rem}.gap-x-1\.5{-moz-column-gap:.375rem;column-gap:.375rem}.gap-y-1\.5{row-gap:.375rem}.gap-2{gap:.5rem}.gap-x-2{-moz-column-gap:.5rem;column-gap:.5rem}.gap-y-2{row-gap:.5rem}.gap-2\.5{gap:.625rem}.gap-x-2\.5{-moz-column-gap:.625rem;column-gap:.625rem}.gap-y-2\.5{row-gap:.625rem}.gap-3{gap:.75rem}.gap-x-3{-moz-column-gap:.75rem;column-gap:.75rem}.gap-y-3{row-gap:.75rem}.gap-3\.5{gap:.875rem}.gap-x-3\.5{-moz-column-gap:.875rem;column-gap:.875rem}.gap-y-3\.5{row-gap:.875rem}.gap-4{gap:1rem}.gap-x-4{-moz-column-gap:1rem;column-gap:1rem}.gap-y-4{row-gap:1rem}.gap-5{gap:1.25rem}.gap-x-5{-moz-column-gap:1.25rem;column-gap:1.25rem}.gap-y-5{row-gap:1.25rem}.gap-6{gap:1.5rem}.gap-x-6{-moz-column-gap:1.5rem;column-gap:1.5rem}.gap-y-6{row-gap:1.5rem}.gap-7{gap:1.75rem}.gap-x-7{-moz-column-gap:1.75rem;column-gap:1.75rem}.gap-y-7{row-gap:1.75rem}.gap-8{gap:2rem}.gap-x-8{-moz-column-gap:2rem;column-gap:2rem}.gap-y-8{row-gap:2rem}.justify-start{justify-content:flex-start}.justify-end{justify-content:flex-end}.justify-center{justify-content:center}.justify-between{justify-content:space-between}.justify-around{justify-content:space-around}.justify-evenly{justify-content:space-evenly}.self-auto{align-self:auto}.self-start{align-self:flex-start}.self-end{align-self:flex-end}.self-center{align-self:center}.self-stretch{align-self:stretch}.self-baseline{align-self:baseline}.content-center{align-content:center}.content-start{align-content:flex-start}.content-end{align-content:flex-end}.content-between{align-content:space-between}.content-around{align-content:space-around}.content-evenly{align-content:space-evenly}.items-start{align-items:flex-start}.items-end{align-items:flex-end}.items-center{align-items:center}.items-baseline{align-items:baseline}.items-stretch{align-items:stretch}@font-face{font-display:fallback;font-family:D-DIN-PRO;font-weight:400;src:url(./fonts/D-DIN-PRO-400-Regular.otf)}@font-face{font-display:fallback;font-family:D-DIN-PRO;font-weight:500;src:url(./fonts/D-DIN-PRO-700-Bold.otf)}.num{font-family:D-DIN-PRO}@font-face{font-display:fallback;font-family:Nunito;font-weight:400;src:url(./fonts/Nunito-Regular.ttf)}@font-face{font-display:fallback;font-family:Nunito;font-weight:700;src:url(./fonts/Nunito-Bold.ttf)}@font-face{font-display:fallback;font-family:Nunito;font-weight:300;src:url(./fonts/Nunito-Light.ttf)}.font-brand{font-family:Nunito;font-weight:400}@supports not (gap:4px){.gap-px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1px*(1 - var(--tw-space-x-reverse)));margin-right:calc(1px*var(--tw-space-x-reverse))}.gap-0\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2px*(1 - var(--tw-space-x-reverse)));margin-right:calc(2px*var(--tw-space-x-reverse))}.gap-3px>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(3px*(1 - var(--tw-space-x-reverse)));margin-right:calc(3px*var(--tw-space-x-reverse))}.gap-1>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}.gap-1\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(6px*(1 - var(--tw-space-x-reverse)));margin-right:calc(6px*var(--tw-space-x-reverse))}.gap-2>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.5rem*var(--tw-space-x-reverse))}.gap-2\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(10px*(1 - var(--tw-space-x-reverse)));margin-right:calc(10px*var(--tw-space-x-reverse))}.gap-3>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.75rem*var(--tw-space-x-reverse))}.gap-3\.5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(14px*(1 - var(--tw-space-x-reverse)));margin-right:calc(14px*var(--tw-space-x-reverse))}.gap-4>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1rem*var(--tw-space-x-reverse))}.gap-5>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.25rem*var(--tw-space-x-reverse))}.gap-6>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.5rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.5rem*var(--tw-space-x-reverse))}.gap-7>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(1.75rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(1.75rem*var(--tw-space-x-reverse))}.gap-8>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(2rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(2rem*var(--tw-space-x-reverse))}.col.gap-px>:not([hidden])~:not([hidden]),.gap-px.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1px*var(--tw-space-y-reverse));margin-top:calc(1px*(1 - var(--tw-space-y-reverse)))}.col.gap-0\.5>:not([hidden])~:not([hidden]),.gap-0\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2px*var(--tw-space-y-reverse));margin-top:calc(2px*(1 - var(--tw-space-y-reverse)))}.col.gap-3px>:not([hidden])~:not([hidden]),.gap-3px.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(3px*var(--tw-space-y-reverse));margin-top:calc(3px*(1 - var(--tw-space-y-reverse)))}.col.gap-1>:not([hidden])~:not([hidden]),.gap-1.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.25rem*var(--tw-space-y-reverse));margin-top:calc(.25rem*(1 - var(--tw-space-y-reverse)))}.col.gap-1\.5>:not([hidden])~:not([hidden]),.gap-1\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(6px*var(--tw-space-y-reverse));margin-top:calc(6px*(1 - var(--tw-space-y-reverse)))}.col.gap-2>:not([hidden])~:not([hidden]),.gap-2.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.5rem*var(--tw-space-y-reverse));margin-top:calc(.5rem*(1 - var(--tw-space-y-reverse)))}.col.gap-2\.5>:not([hidden])~:not([hidden]),.gap-2\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(10px*var(--tw-space-y-reverse));margin-top:calc(10px*(1 - var(--tw-space-y-reverse)))}.col.gap-3>:not([hidden])~:not([hidden]),.gap-3.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(.75rem*var(--tw-space-y-reverse));margin-top:calc(.75rem*(1 - var(--tw-space-y-reverse)))}.col.gap-3\.5>:not([hidden])~:not([hidden]),.gap-3\.5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(14px*var(--tw-space-y-reverse));margin-top:calc(14px*(1 - var(--tw-space-y-reverse)))}.col.gap-4>:not([hidden])~:not([hidden]),.gap-4.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1rem*var(--tw-space-y-reverse));margin-top:calc(1rem*(1 - var(--tw-space-y-reverse)))}.col.gap-5>:not([hidden])~:not([hidden]),.gap-5.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.25rem*var(--tw-space-y-reverse));margin-top:calc(1.25rem*(1 - var(--tw-space-y-reverse)))}.col.gap-6>:not([hidden])~:not([hidden]),.gap-6.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.5rem*var(--tw-space-y-reverse));margin-top:calc(1.5rem*(1 - var(--tw-space-y-reverse)))}.col.gap-7>:not([hidden])~:not([hidden]),.gap-7.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(1.75rem*var(--tw-space-y-reverse));margin-top:calc(1.75rem*(1 - var(--tw-space-y-reverse)))}.col.gap-8>:not([hidden])~:not([hidden]),.gap-8.flex-row>:not([hidden])~:not([hidden]){--tw-space-y-reverse:0;margin-bottom:calc(2rem*var(--tw-space-y-reverse));margin-top:calc(2rem*(1 - var(--tw-space-y-reverse)))}.nav-item>a>:not([hidden])~:not([hidden]){--tw-space-x-reverse:0;margin-left:calc(.25rem*(1 - var(--tw-space-x-reverse)));margin-right:calc(.25rem*var(--tw-space-x-reverse))}}
\ No newline at end of file
diff --git a/www/js/zui3/zui.zentao.js b/www/js/zui3/zui.zentao.js
index f18e6b38bd..680e7bcb41 100644
--- a/www/js/zui3/zui.zentao.js
+++ b/www/js/zui3/zui.zentao.js
@@ -1,8 +1,8 @@
-var Ih=(E,Qt,we)=>{if(!Qt.has(E))throw TypeError("Cannot "+we)};var ve=(E,Qt,we)=>(Ih(E,Qt,"read from private field"),we?we.call(E):Qt.get(E)),Me=(E,Qt,we)=>{if(Qt.has(E))throw TypeError("Cannot add the same private member more than once");Qt instanceof WeakSet?Qt.add(E):Qt.set(E,we)},ze=(E,Qt,we,ma)=>(Ih(E,Qt,"write to private field"),ma?ma.call(E,we):Qt.set(E,we),we);var Dh=(E,Qt,we)=>(Ih(E,Qt,"access private method"),we);(function(E,Qt){typeof exports=="object"&&typeof module<"u"?Qt(exports):typeof define=="function"&&define.amd?define(["exports"],Qt):(E=typeof globalThis<"u"?globalThis:E||self,Qt(E.zui={}))})(this,function(E){var zo,Fo,js,Bs,Hs,Ws,Ks,Vs,jo,cm,Bo,hm,On,zn;"use strict";const Qt="",we="",ma="",$v="",Tv="",Nv="",Ev="",Pv="",Mv="",Av="",Iv="",Dv="",pm="3.0.0",mm="production",nn=document,ar=window,Rh=nn.documentElement,Gn=nn.createElement.bind(nn),Lh=Gn("div"),ga=Gn("table"),gm=Gn("tbody"),Oh=Gn("tr"),{isArray:lr,prototype:zh}=Array,{concat:ym,filter:ya,indexOf:Fh,map:jh,push:_m,slice:Bh,some:_a,splice:bm}=zh,vm=/^#(?:[\w-]|\\.|[^\x00-\xa0])*$/,wm=/^\.(?:[\w-]|\\.|[^\x00-\xa0])*$/,Cm=/<.+>/,km=/^\w+$/;function ba(i,t){const e=Sm(t);return!i||!e&&!Yn(t)&&!Jt(t)?[]:!e&&wm.test(i)?t.getElementsByClassName(i.slice(1).replace(/\\/g,"")):!e&&km.test(i)?t.getElementsByTagName(i):t.querySelectorAll(i)}class cr{constructor(t,e){if(!t)return;if(va(t))return t;let n=t;if(de(t)){const s=e||nn;if(n=vm.test(t)&&Yn(s)?s.getElementById(t.slice(1).replace(/\\/g,"")):Cm.test(t)?qh(t):va(s)?s.find(t):de(s)?g(s).find(t):ba(t,s),!n)return}else if(Qn(t))return this.ready(t);(n.nodeType||n===ar)&&(n=[n]),this.length=n.length;for(let s=0,r=this.length;s{for(;t.firstChild;)t.removeChild(t.firstChild)})};function hr(...i){const t=$m(i[0])?i.shift():!1,e=i.shift(),n=i.length;if(!e)return{};if(!n)return hr(t,g,e);for(let s=0;s{Jt(r)&&re(e,(o,a)=>{n?t?r.classList.add(a):r.classList.remove(a):r.classList.toggle(a)})})},st.addClass=function(i){return this.toggleClass(i,!0)},st.removeAttr=function(i){const t=ur(i);return this.each((e,n)=>{Jt(n)&&re(t,(s,r)=>{n.removeAttribute(r)})})};function Nm(i,t){if(i){if(de(i)){if(arguments.length<2){if(!this[0]||!Jt(this[0]))return;const e=this[0].getAttribute(i);return es(e)?void 0:e}return Ce(t)?this:es(t)?this.removeAttr(i):this.each((e,n)=>{Jt(n)&&n.setAttribute(i,t)})}for(const e in i)this.attr(e,i[e]);return this}}st.attr=Nm,st.removeClass=function(i){return arguments.length?this.toggleClass(i,!1):this.attr("class","")},st.hasClass=function(i){return!!i&&_a.call(this,t=>Jt(t)&&t.classList.contains(i))},st.get=function(i){return Ce(i)?Bh.call(this):(i=Number(i),this[i<0?i+this.length:i])},st.eq=function(i){return g(this.get(i))},st.first=function(){return this.eq(0)},st.last=function(){return this.eq(-1)};function Em(i){return Ce(i)?this.get().map(t=>Jt(t)||xm(t)?t.textContent:"").join(""):this.each((t,e)=>{Jt(e)&&(e.textContent=i)})}st.text=Em;function sn(i,t,e){if(!Jt(i))return;const n=ar.getComputedStyle(i,null);return e?n.getPropertyValue(t)||void 0:n[t]||i.style[t]}function Ke(i,t){return parseInt(sn(i,t),10)||0}function Wh(i,t){return Ke(i,`border${t?"Left":"Top"}Width`)+Ke(i,`padding${t?"Left":"Top"}`)+Ke(i,`padding${t?"Right":"Bottom"}`)+Ke(i,`border${t?"Right":"Bottom"}Width`)}const Ca={};function Pm(i){if(Ca[i])return Ca[i];const t=Gn(i);nn.body.insertBefore(t,null);const e=sn(t,"display");return nn.body.removeChild(t),Ca[i]=e!=="none"?e:"block"}function Kh(i){return sn(i,"display")==="none"}function Vh(i,t){const e=i&&(i.matches||i.webkitMatchesSelector||i.msMatchesSelector);return!!e&&!!t&&e.call(i,t)}function dr(i){return de(i)?(t,e)=>Vh(e,i):Qn(i)?i:va(i)?(t,e)=>i.is(e):i?(t,e)=>e===i:()=>!1}st.filter=function(i){const t=dr(i);return g(ya.call(this,(e,n)=>t.call(e,n,e)))};function yn(i,t){return t?i.filter(t):i}st.detach=function(i){return yn(this,i).each((t,e)=>{e.parentNode&&e.parentNode.removeChild(e)}),this};const Mm=/^\s*<(\w+)[^>]*>/,Am=/^<(\w+)\s*\/?>(?:<\/\1>)?$/,Uh={"*":Lh,tr:gm,td:Oh,th:Oh,thead:ga,tbody:ga,tfoot:ga};function qh(i){if(!de(i))return[];if(Am.test(i))return[Gn(RegExp.$1)];const t=Mm.test(i)&&RegExp.$1,e=Uh[t]||Uh["*"];return e.innerHTML=i,g(e.childNodes).detach().get()}g.parseHTML=qh,st.has=function(i){const t=de(i)?(e,n)=>ba(i,n).length:(e,n)=>n.contains(i);return this.filter(t)},st.not=function(i){const t=dr(i);return this.filter((e,n)=>(!de(i)||Jt(n))&&!t.call(n,e,n))};function rn(i,t,e,n){const s=[],r=Qn(t),o=n&&dr(n);for(let a=0,l=i.length;at.selected&&!t.disabled&&!t.parentNode.disabled),"value"):i.value||""}function Im(i){return arguments.length?this.each((t,e)=>{const n=e.multiple&&e.options;if(n||ru.test(e.type)){const s=lr(i)?jh.call(i,String):es(i)?[]:[String(i)];n?re(e.options,(r,o)=>{o.selected=s.indexOf(o.value)>=0},!0):e.checked=s.indexOf(e.value)>=0}else e.value=Ce(i)||es(i)?"":i}):this[0]&&Gh(this[0])}st.val=Im,st.is=function(i){const t=dr(i);return _a.call(this,(e,n)=>t.call(e,n,e))},g.guid=1;function Ve(i){return i.length>1?ya.call(i,(t,e,n)=>Fh.call(n,t)===e):i}g.unique=Ve,st.add=function(i,t){return g(Ve(this.get().concat(g(i,t).get())))},st.children=function(i){return yn(g(Ve(rn(this,t=>t.children))),i)},st.parent=function(i){return yn(g(Ve(rn(this,"parentNode"))),i)},st.index=function(i){const t=i?g(i)[0]:this[0],e=i?this:g(t).parent().children();return Fh.call(e,t)},st.closest=function(i){const t=this.filter(i);if(t.length)return t;const e=this.parent();return e.length?e.closest(i):t},st.siblings=function(i){return yn(g(Ve(rn(this,t=>g(t).parent().children().not(t)))),i)},st.find=function(i){return g(Ve(rn(this,t=>ba(i,t))))};const Dm=/^\s*\s*$/g,Rm=/^$|^module$|\/(java|ecma)script/i,Lm=["type","src","nonce","noModule"];function Om(i,t){const e=g(i);e.filter("script").add(e.find("script")).each((n,s)=>{if(Rm.test(s.type)&&Rh.contains(s)){const r=Gn("script");r.text=s.textContent.replace(Dm,""),re(Lm,(o,a)=>{s[a]&&(r[a]=s[a])}),t.head.insertBefore(r,null),t.head.removeChild(r)}})}function zm(i,t,e,n,s){n?i.insertBefore(t,e?i.firstChild:null):i.nodeName==="HTML"?i.parentNode.replaceChild(t,i):i.parentNode.insertBefore(t,e?i:i.nextSibling),s&&Om(t,i.ownerDocument)}function _n(i,t,e,n,s,r,o,a){return re(i,(l,h)=>{re(g(h),(f,d)=>{re(g(t),(m,y)=>{const v=e?d:y,S=e?y:d,x=e?f:m;zm(v,x?S.cloneNode(!0):S,n,s,!x)},a)},o)},r),t}st.after=function(){return _n(arguments,this,!1,!1,!1,!0,!0)},st.append=function(){return _n(arguments,this,!1,!1,!0)};function Fm(i){if(!arguments.length)return this[0]&&this[0].innerHTML;if(Ce(i))return this;const t=/