/**
	 * Prepares a new package installation queue.
	 * 
	 * @return	array<integer>
	 */
	public function prepareQueue() {
		$processNo = PackageInstallationQueue::getNewProcessNo();
		
		$queue = PackageInstallationQueueEditor::create(array(
			'processNo' => $processNo,
			'userID' => WCF::getUser()->userID,
			'package' => $this->package->package,
			'packageName' => $this->package->packageName,
			'packageID' => $this->package->packageID,
			'action' => $this->parameters['action'],
			'installationType' => 'other'
		));
		
		return array(
			'queueID' => $queue->queueID
		);
	}
 /**
  * Prepares the uninstallation process.
  */
 protected function stepPrepare()
 {
     $package = new Package($this->packageID);
     if (!$package->packageID) {
         throw new IllegalLinkException();
     }
     // get new process no
     $processNo = PackageInstallationQueue::getNewProcessNo();
     // create queue
     $queue = PackageInstallationQueueEditor::create(array('processNo' => $processNo, 'userID' => WCF::getUser()->userID, 'packageName' => $package->getName(), 'packageID' => $package->packageID, 'action' => 'uninstall', 'cancelable' => 0));
     // initialize uninstallation
     $this->installation = new PackageUninstallationDispatcher($queue);
     $this->installation->nodeBuilder->purgeNodes();
     $this->installation->nodeBuilder->buildNodes();
     WCF::getTPL()->assign(array('queue' => $queue));
     $queueID = $this->installation->nodeBuilder->getQueueByNode($queue->processNo, $this->installation->nodeBuilder->getNextNode());
     $this->data = array('template' => WCF::getTPL()->fetch($this->templateName), 'step' => 'uninstall', 'node' => $this->installation->nodeBuilder->getNextNode(), 'currentAction' => WCF::getLanguage()->get('wcf.package.installation.step.uninstalling'), 'progress' => 0, 'queueID' => $queueID);
 }
 /**
  * Uninstalls the specified package.
  * $package may either be the packageID or the package identifier.
  * 
  * @param	mixed	$package
  */
 private function uninstall($package)
 {
     if (Package::isValidPackageName($package)) {
         $packageID = PackageCache::getInstance()->getPackageID($package);
     } else {
         $packageID = $package;
     }
     // UninstallPackageAction::prepare()
     $package = new Package($packageID);
     if (!$package->packageID || !$package->canUninstall()) {
         $this->error('invalidUninstallation');
     }
     // get new process no
     $processNo = PackageInstallationQueue::getNewProcessNo();
     // create queue
     $queue = PackageInstallationQueueEditor::create(array('processNo' => $processNo, 'userID' => CLIWCF::getUser()->userID, 'packageName' => $package->getName(), 'packageID' => $package->packageID, 'action' => 'uninstall'));
     // initialize uninstallation
     $installation = new PackageUninstallationDispatcher($queue);
     $installation->nodeBuilder->purgeNodes();
     $installation->nodeBuilder->buildNodes();
     CLIWCF::getTPL()->assign(array('queue' => $queue));
     $queueID = $installation->nodeBuilder->getQueueByNode($queue->processNo, $installation->nodeBuilder->getNextNode());
     $step = 'uninstall';
     $node = $installation->nodeBuilder->getNextNode();
     $currentAction = CLIWCF::getLanguage()->get('wcf.package.installation.step.uninstalling');
     $progress = 0;
     // initialize progressbar
     $progressbar = new ProgressBar(new ConsoleProgressBar(array('width' => CLIWCF::getTerminal()->getWidth(), 'elements' => array(ConsoleProgressBar::ELEMENT_PERCENT, ConsoleProgressBar::ELEMENT_BAR, ConsoleProgressBar::ELEMENT_TEXT), 'textWidth' => min(floor(CLIWCF::getTerminal()->getWidth() / 2), 50))));
     // InstallPackageAction::readParameters()
     $finished = false;
     while (!$finished) {
         $queue = new PackageInstallationQueue($queueID);
         $installation = new PackageUninstallationDispatcher($queue);
         switch ($step) {
             case 'uninstall':
                 $_node = $installation->uninstall($node);
                 if ($_node == '') {
                     // remove node data
                     $installation->nodeBuilder->purgeNodes();
                     // UninstallPackageAction::finalize()
                     CacheHandler::getInstance()->flushAll();
                     // /UninstallPackageAction::finalize()
                     // show success
                     $currentAction = CLIWCF::getLanguage()->get('wcf.acp.package.uninstallation.step.success');
                     $progress = 100;
                     $step = 'success';
                     $finished = true;
                     continue;
                 }
                 // continue with next node
                 $queueID = $installation->nodeBuilder->getQueueByNode($installation->queue->processNo, $installation->nodeBuilder->getNextNode($node));
                 $step = 'uninstall';
                 $progress = $installation->nodeBuilder->calculateProgress($node);
                 $node = $_node;
         }
         $progressbar->update($progress, $currentAction);
     }
     $progressbar->getAdapter()->finish();
 }
 /**
  * Creates a new package installation queue.
  * 
  * @param	string		$queueType
  * @return	array
  */
 protected function createQueue($queueType)
 {
     if (isset($this->parameters['authData'])) {
         PackageUpdateServer::storeAuthData($this->parameters['authData']['packageUpdateServerID'], $this->parameters['authData']['username'], $this->parameters['authData']['password'], $this->parameters['authData']['saveCredentials']);
     }
     $scheduler = new PackageInstallationScheduler($this->parameters['packages']);
     try {
         $scheduler->buildPackageInstallationStack($queueType == 'install');
     } catch (PackageUpdateUnauthorizedException $e) {
         return array('template' => $e->getRenderedTemplate());
     }
     // validate exclusions
     if ($queueType == 'update') {
         $excludedPackages = $scheduler->getExcludedPackages();
         if (!empty($excludedPackages)) {
             return array('excludedPackages' => true, 'template' => WCF::getTPL()->fetch('packageUpdateExcludedPackages', 'wcf', array('excludedPackages' => $excludedPackages)));
         }
     }
     $stack = $scheduler->getPackageInstallationStack();
     $queueID = null;
     if (!empty($stack)) {
         $parentQueueID = 0;
         $processNo = PackageInstallationQueue::getNewProcessNo();
         foreach ($stack as $package) {
             $queue = PackageInstallationQueueEditor::create(array('parentQueueID' => $parentQueueID, 'processNo' => $processNo, 'userID' => WCF::getUser()->userID, 'package' => $package['package'], 'packageName' => $package['packageName'], 'packageID' => $package['packageID'] ?: null, 'archive' => $package['archive'], 'action' => $package['action']));
             $parentQueueID = $queue->queueID;
             if ($queueID === null) {
                 $queueID = $queue->queueID;
             }
         }
     }
     return array('queueID' => $queueID);
 }
	/**
	 * @see	wcf\form\IForm::save()
	 */
	public function save() {
		parent::save();
		
		// get new process no
		$processNo = PackageInstallationQueue::getNewProcessNo();
		
		// obey foreign key
		$packageID = ($this->packageID) ? $this->packageID : null;
		
		// insert queue
		$this->queue = PackageInstallationQueueEditor::create(array(
			'processNo' => $processNo,
			'userID' => WCF::getUser()->userID,
			'package' => $this->archive->getPackageInfo('name'),
			'packageName' => $this->archive->getLocalizedPackageInfo('packageName'),
			'packageID' => $packageID,
			'archive' => (!empty($this->uploadPackage['tmp_name']) ? $this->uploadPackage['name'] : $this->downloadPackage),
			'action' => ($this->package != null ? 'update' : 'install'),
			'confirmInstallation' => 1
		));
		
		$this->saved();
		
		// open queue
		PackageInstallationDispatcher::openQueue(0, $processNo);
	}
 /**
  * @see wcf\form\IForm::save()
  */
 public function save()
 {
     parent::save();
     // get new process no
     $processNo = PackageInstallationQueue::getNewProcessNo();
     // obey foreign key
     $packageID = $this->packageID ? $this->packageID : null;
     // insert queue
     $this->queue = PackageInstallationQueueEditor::create(array('processNo' => $processNo, 'userID' => WCF::getUser()->userID, 'package' => $this->archive->getPackageInfo('name'), 'packageName' => $this->archive->getLocalizedPackageInfo('packageName'), 'packageID' => $packageID, 'archive' => !empty($this->uploadPackage['tmp_name']) ? $this->uploadPackage['name'] : $this->downloadPackage, 'action' => $this->package != null ? 'update' : 'install', 'confirmInstallation' => 1, 'cancelable' => $this->package != null ? 0 : 1));
     $this->saved();
     // open queue
     $url = LinkHandler::getInstance()->getLink('Package', array(), 'action=openQueue&processNo=' . $processNo);
     HeaderUtil::redirect($url);
     exit;
 }
 /**
  * Adds an uninstall entry to the package installation queue.
  *
  * @param	Package		$package
  * @param	array		$packages
  */
 public static function addQueueEntries(Package $package, $packages = array())
 {
     // get new process no
     $processNo = PackageInstallationQueue::getNewProcessNo();
     // add dependent packages to queue
     $statementParameters = array();
     foreach ($packages as $dependentPackage) {
         $statementParameters[] = array('packageName' => $dependentPackage['packageName'], 'packageID' => $dependentPackage['packageID']);
     }
     // add uninstalling package to queue
     $statementParameters[] = array('packageName' => $package->getName(), 'packageID' => $package->packageID);
     // insert queue entry (entries)
     $sql = "INSERT INTO\twcf" . WCF_N . "_package_installation_queue\n\t\t\t\t\t(processNo, userID, package, packageID, action)\n\t\t\tVALUES\t\t(?, ?, ?, ?, ?)";
     $statement = WCF::getDB()->prepareStatement($sql);
     foreach ($statementParameters as $parameter) {
         $statement->execute(array($processNo, WCF::getUser()->userID, $parameter['packageName'], $parameter['packageID'], 'uninstall'));
     }
     $url = LinkHandler::getInstance()->getLink('Package', array(), 'action=openQueue&processNo=' . $processNo);
     HeaderUtil::redirect($url);
     exit;
 }
 /**
  * @see	\wcf\form\IForm::save()
  */
 public function save()
 {
     parent::save();
     // get new process no
     $processNo = PackageInstallationQueue::getNewProcessNo();
     // obey foreign key
     $packageID = $this->package ? $this->package->packageID : null;
     $archive = $this->downloadPackage;
     if ($this->stylePackageImportLocation) {
         $archive = $this->stylePackageImportLocation;
     } else {
         if (!empty($this->uploadPackage['tmp_name'])) {
             $archive = $this->uploadPackage['name'];
         }
     }
     // insert queue
     $isApplication = PackageValidationManager::getInstance()->getPackageValidationArchive()->getArchive()->getPackageInfo('isApplication');
     $this->queue = PackageInstallationQueueEditor::create(array('processNo' => $processNo, 'userID' => WCF::getUser()->userID, 'package' => PackageValidationManager::getInstance()->getPackageValidationArchive()->getArchive()->getPackageInfo('name'), 'packageName' => PackageValidationManager::getInstance()->getPackageValidationArchive()->getArchive()->getLocalizedPackageInfo('packageName'), 'packageID' => $packageID, 'archive' => $archive, 'action' => $this->package != null ? 'update' : 'install', 'isApplication' => !$isApplication ? '0' : '1'));
     $this->saved();
     // open queue
     PackageInstallationDispatcher::openQueue(0, $processNo);
 }
	/**
	 * Adds an uninstall entry to the package installation queue.
	 * 
	 * @param	Package		$package
	 * @param	array		$packages
	 */
	public static function addQueueEntries(Package $package, $packages = array()) {
		// get new process no
		$processNo = PackageInstallationQueue::getNewProcessNo();
		
		// add dependent packages to queue
		$statementParameters = array();
		foreach ($packages as $dependentPackage) {
			$statementParameters[] = array(
				'packageName' => $dependentPackage['packageName'],
				'packageID' => $dependentPackage['packageID']
			);
		}
		
		// add uninstalling package to queue
		$statementParameters[] = array(
			'packageName' => $package->getName(),
			'packageID' => $package->packageID
		);
		
		// insert queue entry (entries)
		$sql = "INSERT INTO	wcf".WCF_N."_package_installation_queue
					(processNo, userID, package, packageID, action)
			VALUES		(?, ?, ?, ?, ?)";
		$statement = WCF::getDB()->prepareStatement($sql);
		foreach ($statementParameters as $parameter) {
			$statement->execute(array(
				$processNo,
				WCF::getUser()->userID,
				$parameter['packageName'],
				$parameter['packageID'],
				'uninstall'
			));
		}
		
		self::openQueue(0, $processNo);
	}