public function produceAphrontResponse() { $controller = $this->getController(); if (!$this->getApplicationMenu()) { $application_menu = $controller->buildApplicationMenu(); if ($application_menu) { $this->setApplicationMenu($application_menu); } } $viewer = $this->getUser(); if ($viewer && $viewer->getPHID()) { $object_phids = $this->pageObjects; foreach ($object_phids as $object_phid) { PhabricatorFeedStoryNotification::updateObjectNotificationViews($viewer, $object_phid); } } if ($this->getRequest()->isQuicksand()) { $content = $this->renderForQuicksand(); $response = id(new AphrontAjaxResponse())->setContent($content); } else { $content = $this->render(); $response = id(new AphrontWebpageResponse())->setContent($content); } return $response; }
public function processRequest() { $request = $this->getRequest(); $user = $request->getUser(); $viewer_is_anonymous = !$user->isLoggedIn(); $revision = id(new DifferentialRevision())->load($this->revisionID); if (!$revision) { return new Aphront404Response(); } $revision->loadRelationships(); $diffs = $revision->loadDiffs(); if (!$diffs) { throw new Exception("This revision has no diffs. Something has gone quite wrong."); } $diff_vs = $request->getInt('vs'); $target_id = $request->getInt('id'); $target = idx($diffs, $target_id, end($diffs)); $target_manual = $target; if (!$target_id) { foreach ($diffs as $diff) { if ($diff->getCreationMethod() != 'commit') { $target_manual = $diff; } } } if (empty($diffs[$diff_vs])) { $diff_vs = null; } $arc_project = $target->loadArcanistProject(); $repository = $arc_project ? $arc_project->loadRepository() : null; list($changesets, $vs_map, $vs_changesets, $rendering_references) = $this->loadChangesetsAndVsMap($target, idx($diffs, $diff_vs), $repository); if ($request->getExists('download')) { return $this->buildRawDiffResponse($changesets, $vs_changesets, $vs_map, $repository); } list($aux_fields, $props) = $this->loadAuxiliaryFieldsAndProperties($revision, $target_manual, array('local:commits', 'arc:lint', 'arc:unit')); $comments = $revision->loadComments(); $comments = array_merge($this->getImplicitComments($revision, reset($diffs)), $comments); $all_changesets = $changesets; $inlines = $this->loadInlineComments($comments, $all_changesets); $object_phids = array_merge($revision->getReviewers(), $revision->getCCPHIDs(), $revision->loadCommitPHIDs(), array($revision->getAuthorPHID(), $user->getPHID()), mpull($comments, 'getAuthorPHID')); foreach ($comments as $comment) { $metadata = $comment->getMetadata(); $added_reviewers = idx($metadata, DifferentialComment::METADATA_ADDED_REVIEWERS); if ($added_reviewers) { foreach ($added_reviewers as $phid) { $object_phids[] = $phid; } } $added_ccs = idx($metadata, DifferentialComment::METADATA_ADDED_CCS); if ($added_ccs) { foreach ($added_ccs as $phid) { $object_phids[] = $phid; } } } foreach ($revision->getAttached() as $type => $phids) { foreach ($phids as $phid => $info) { $object_phids[] = $phid; } } $aux_phids = array(); foreach ($aux_fields as $key => $aux_field) { $aux_phids[$key] = $aux_field->getRequiredHandlePHIDsForRevisionView(); } $object_phids = array_merge($object_phids, array_mergev($aux_phids)); $object_phids = array_unique($object_phids); $handles = id(new PhabricatorObjectHandleData($object_phids))->loadHandles(); foreach ($aux_fields as $key => $aux_field) { // Make sure each field only has access to handles it specifically // requested, not all handles. Otherwise you can get a field which works // only in the presence of other fields. $aux_field->setHandles(array_select_keys($handles, $aux_phids[$key])); } $reviewer_warning = null; $has_live_reviewer = false; foreach ($revision->getReviewers() as $reviewer) { if (!$handles[$reviewer]->isDisabled()) { $has_live_reviewer = true; } } if (!$has_live_reviewer) { $reviewer_warning = new AphrontErrorView(); $reviewer_warning->setSeverity(AphrontErrorView::SEVERITY_WARNING); $reviewer_warning->setTitle('No Active Reviewers'); if ($revision->getReviewers()) { $reviewer_warning->appendChild('<p>All specified reviewers are disabled. You may want to add ' . 'some new reviewers.</p>'); } else { $reviewer_warning->appendChild('<p>This revision has no specified reviewers. You may want to ' . 'add some.</p>'); } } $request_uri = $request->getRequestURI(); $limit = 100; $large = $request->getStr('large'); if (count($changesets) > $limit && !$large) { $count = number_format(count($changesets)); $warning = new AphrontErrorView(); $warning->setTitle('Very Large Diff'); $warning->setSeverity(AphrontErrorView::SEVERITY_WARNING); $warning->setWidth(AphrontErrorView::WIDTH_WIDE); $warning->appendChild("<p>This diff is very large and affects {$count} files. Load " . "each file individually. " . "<strong>" . phutil_render_tag('a', array('href' => $request_uri->alter('large', 'true')->setFragment('toc')), 'Show All Files Inline') . "</strong>"); $warning = $warning->render(); $my_inlines = id(new DifferentialInlineComment())->loadAllWhere('revisionID = %d AND commentID IS NULL AND authorPHID = %s AND ' . 'changesetID IN (%Ld)', $this->revisionID, $user->getPHID(), mpull($changesets, 'getID')); $visible_changesets = array(); foreach ($inlines + $my_inlines as $inline) { $changeset_id = $inline->getChangesetID(); if (isset($changesets[$changeset_id])) { $visible_changesets[$changeset_id] = $changesets[$changeset_id]; } } if (!empty($props['arc:lint'])) { $changeset_paths = mpull($changesets, null, 'getFilename'); foreach ($props['arc:lint'] as $lint) { $changeset = idx($changeset_paths, $lint['path']); if ($changeset) { $visible_changesets[$changeset->getID()] = $changeset; } } } } else { $warning = null; $visible_changesets = $changesets; } $revision_detail = new DifferentialRevisionDetailView(); $revision_detail->setRevision($revision); $revision_detail->setAuxiliaryFields($aux_fields); $actions = $this->getRevisionActions($revision); $custom_renderer_class = PhabricatorEnv::getEnvConfig('differential.revision-custom-detail-renderer'); if ($custom_renderer_class) { // TODO: build a better version of the action links and deprecate the // whole DifferentialRevisionDetailRenderer class. $custom_renderer = newv($custom_renderer_class, array()); $custom_renderer->setDiff($target); if ($diff_vs) { $custom_renderer->setVSDiff($diffs[$diff_vs]); } $actions = array_merge($actions, $custom_renderer->generateActionLinks($revision, $target_manual)); } $whitespace = $request->getStr('whitespace', DifferentialChangesetParser::WHITESPACE_IGNORE_ALL); if ($arc_project) { list($symbol_indexes, $project_phids) = $this->buildSymbolIndexes($arc_project, $visible_changesets); } else { $symbol_indexes = array(); $project_phids = null; } $revision_detail->setActions($actions); $revision_detail->setUser($user); $comment_view = new DifferentialRevisionCommentListView(); $comment_view->setComments($comments); $comment_view->setHandles($handles); $comment_view->setInlineComments($inlines); $comment_view->setChangesets($all_changesets); $comment_view->setUser($user); $comment_view->setTargetDiff($target); $comment_view->setVersusDiffID($diff_vs); if ($arc_project) { Javelin::initBehavior('repository-crossreference', array('section' => $comment_view->getID(), 'projects' => $project_phids)); } $changeset_view = new DifferentialChangesetListView(); $changeset_view->setChangesets($changesets); $changeset_view->setVisibleChangesets($visible_changesets); if (!$viewer_is_anonymous) { $changeset_view->setInlineCommentControllerURI('/differential/comment/inline/edit/' . $revision->getID() . '/'); } $changeset_view->setStandaloneURI('/differential/changeset/'); $changeset_view->setRawFileURIs('/differential/changeset/?view=old', '/differential/changeset/?view=new'); $changeset_view->setUser($user); $changeset_view->setDiff($target); $changeset_view->setRenderingReferences($rendering_references); $changeset_view->setVsMap($vs_map); $changeset_view->setWhitespace($whitespace); if ($repository) { $changeset_view->setRepository($repository); } $changeset_view->setSymbolIndexes($symbol_indexes); $diff_history = new DifferentialRevisionUpdateHistoryView(); $diff_history->setDiffs($diffs); $diff_history->setSelectedVersusDiffID($diff_vs); $diff_history->setSelectedDiffID($target->getID()); $diff_history->setSelectedWhitespace($whitespace); $diff_history->setUser($user); $local_view = new DifferentialLocalCommitsView(); $local_view->setUser($user); $local_view->setLocalCommits(idx($props, 'local:commits')); if ($repository) { $other_revisions = $this->loadOtherRevisions($changesets, $target, $repository); } else { $other_revisions = array(); } $other_view = null; if ($other_revisions) { $other_view = $this->renderOtherRevisions($other_revisions); } $toc_view = new DifferentialDiffTableOfContentsView(); $toc_view->setChangesets($changesets); $toc_view->setVisibleChangesets($visible_changesets); $toc_view->setRenderingReferences($rendering_references); $toc_view->setUnitTestData(idx($props, 'arc:unit', array())); if ($repository) { $toc_view->setRepository($repository); } $toc_view->setDiff($target); $toc_view->setUser($user); $toc_view->setRevisionID($revision->getID()); $toc_view->setWhitespace($whitespace); $comment_form = null; if (!$viewer_is_anonymous) { $draft = id(new PhabricatorDraft())->loadOneWhere('authorPHID = %s AND draftKey = %s', $user->getPHID(), 'differential-comment-' . $revision->getID()); if ($draft) { $draft = $draft->getDraft(); } else { $draft = null; } $comment_form = new DifferentialAddCommentView(); $comment_form->setRevision($revision); $comment_form->setAuxFields($aux_fields); $comment_form->setActions($this->getRevisionCommentActions($revision)); $comment_form->setActionURI('/differential/comment/save/'); $comment_form->setUser($user); $comment_form->setDraft($draft); } $pane_id = celerity_generate_unique_node_id(); Javelin::initBehavior('differential-keyboard-navigation', array('haunt' => $pane_id)); Javelin::initBehavior('differential-user-select'); $page_pane = id(new DifferentialPrimaryPaneView())->setLineWidthFromChangesets($changesets)->setID($pane_id)->appendChild($comment_view->render() . $diff_history->render() . $warning . $local_view->render() . $toc_view->render() . $other_view . $changeset_view->render()); if ($comment_form) { $page_pane->appendChild($comment_form->render()); } PhabricatorFeedStoryNotification::updateObjectNotificationViews($user, $revision->getPHID()); $top_anchor = id(new PhabricatorAnchorView())->setAnchorName('top')->setNavigationMarker(true); $nav = $this->buildSideNavView($revision, $changesets); $nav->selectFilter(''); $nav->appendChild(array($reviewer_warning, $top_anchor, $revision_detail, $page_pane)); return $this->buildApplicationPage($nav, array('title' => 'D' . $revision->getID() . ' ' . $revision->getTitle())); }
public function buildApplicationPage($view, array $options) { $page = $this->buildStandardPageView(); $title = PhabricatorEnv::getEnvConfig('phabricator.serious-business') ? 'Phabricator' : pht('Bacon Ice Cream for Breakfast'); $application = $this->getCurrentApplication(); $page->setTitle(idx($options, 'title', $title)); if ($application) { $page->setApplicationName($application->getName()); if ($application->getTitleGlyph()) { $page->setGlyph($application->getTitleGlyph()); } } if (idx($options, 'class')) { $page->addClass($options['class']); } if (!$view instanceof AphrontSideNavFilterView) { $nav = new AphrontSideNavFilterView(); $nav->appendChild($view); $view = $nav; } $user = $this->getRequest()->getUser(); $view->setUser($user); $page->appendChild($view); $object_phids = idx($options, 'pageObjects', array()); if ($object_phids) { $page->appendPageObjects($object_phids); foreach ($object_phids as $object_phid) { PhabricatorFeedStoryNotification::updateObjectNotificationViews($user, $object_phid); } } if (idx($options, 'device', true)) { $page->setDeviceReady(true); } $page->setShowFooter(idx($options, 'showFooter', true)); $page->setShowChrome(idx($options, 'chrome', true)); $application_menu = $this->buildApplicationMenu(); if ($application_menu) { $page->setApplicationMenu($application_menu); } return $this->buildPageResponse($page); }
public function processRequest() { $request = $this->getRequest(); $user = $request->getUser(); $e_title = null; $priority_map = ManiphestTaskPriority::getTaskPriorityMap(); $task = id(new ManiphestTask())->load($this->id); if (!$task) { return new Aphront404Response(); } $workflow = $request->getStr('workflow'); $parent_task = null; if ($workflow && is_numeric($workflow)) { $parent_task = id(new ManiphestTask())->load($workflow); } $transactions = id(new ManiphestTransaction())->loadAllWhere('taskID = %d ORDER BY id ASC', $task->getID()); $e_commit = PhabricatorEdgeConfig::TYPE_TASK_HAS_COMMIT; $e_dep_on = PhabricatorEdgeConfig::TYPE_TASK_DEPENDS_ON_TASK; $e_dep_by = PhabricatorEdgeConfig::TYPE_TASK_DEPENDED_ON_BY_TASK; $e_rev = PhabricatorEdgeConfig::TYPE_TASK_HAS_RELATED_DREV; $phid = $task->getPHID(); $query = id(new PhabricatorEdgeQuery())->withSourcePHIDs(array($phid))->withEdgeTypes(array($e_commit, $e_dep_on, $e_dep_by, $e_rev)); $edges = $query->execute(); $commit_phids = array_keys($edges[$phid][$e_commit]); $dep_on_tasks = array_keys($edges[$phid][$e_dep_on]); $dep_by_tasks = array_keys($edges[$phid][$e_dep_by]); $revs = array_keys($edges[$phid][$e_rev]); $phids = array_fill_keys($query->getDestinationPHIDs(), true); foreach ($transactions as $transaction) { foreach ($transaction->extractPHIDs() as $phid) { $phids[$phid] = true; } } foreach ($task->getCCPHIDs() as $phid) { $phids[$phid] = true; } foreach ($task->getProjectPHIDs() as $phid) { $phids[$phid] = true; } if ($task->getOwnerPHID()) { $phids[$task->getOwnerPHID()] = true; } $phids[$task->getAuthorPHID()] = true; $attached = $task->getAttached(); foreach ($attached as $type => $list) { foreach ($list as $phid => $info) { $phids[$phid] = true; } } if ($parent_task) { $phids[$parent_task->getPHID()] = true; } $phids = array_keys($phids); $handles = $this->loadViewerHandles($phids); $dict = array(); $dict['Status'] = '<strong>' . ManiphestTaskStatus::getTaskStatusFullName($task->getStatus()) . '</strong>'; $dict['Assigned To'] = $task->getOwnerPHID() ? $handles[$task->getOwnerPHID()]->renderLink() : '<em>None</em>'; $dict['Priority'] = ManiphestTaskPriority::getTaskPriorityName($task->getPriority()); $cc = $task->getCCPHIDs(); if ($cc) { $cc_links = array(); foreach ($cc as $phid) { $cc_links[] = $handles[$phid]->renderLink(); } $dict['CC'] = implode(', ', $cc_links); } else { $dict['CC'] = '<em>None</em>'; } $dict['Author'] = $handles[$task->getAuthorPHID()]->renderLink(); $source = $task->getOriginalEmailSource(); if ($source) { $subject = '[T' . $task->getID() . '] ' . $task->getTitle(); $dict['From Email'] = phutil_render_tag('a', array('href' => 'mailto:' . $source . '?subject=' . $subject), phutil_escape_html($source)); } $projects = $task->getProjectPHIDs(); if ($projects) { $project_links = array(); foreach ($projects as $phid) { $project_links[] = $handles[$phid]->renderLink(); } $dict['Projects'] = implode(', ', $project_links); } else { $dict['Projects'] = '<em>None</em>'; } $extensions = ManiphestTaskExtensions::newExtensions(); $aux_fields = $extensions->getAuxiliaryFieldSpecifications(); if ($aux_fields) { $task->loadAndAttachAuxiliaryAttributes(); foreach ($aux_fields as $aux_field) { $aux_key = $aux_field->getAuxiliaryKey(); $aux_field->setValue($task->getAuxiliaryAttribute($aux_key)); $value = $aux_field->renderForDetailView(); if (strlen($value)) { $dict[$aux_field->getLabel()] = $value; } } } if ($dep_by_tasks) { $dict['Dependent Tasks'] = $this->renderHandleList(array_select_keys($handles, $dep_by_tasks)); } if ($dep_on_tasks) { $dict['Depends On'] = $this->renderHandleList(array_select_keys($handles, $dep_on_tasks)); } if ($revs) { $dict['Revisions'] = $this->renderHandleList(array_select_keys($handles, $revs)); } if ($commit_phids) { $dict['Commits'] = $this->renderHandleList(array_select_keys($handles, $commit_phids)); } $file_infos = idx($attached, PhabricatorPHIDConstants::PHID_TYPE_FILE); if ($file_infos) { $file_phids = array_keys($file_infos); $files = id(new PhabricatorFile())->loadAllWhere('phid IN (%Ls)', $file_phids); $views = array(); foreach ($files as $file) { $view = new AphrontFilePreviewView(); $view->setFile($file); $views[] = $view->render(); } $dict['Files'] = implode('', $views); } $context_bar = null; if ($parent_task) { $context_bar = new AphrontContextBarView(); $context_bar->addButton(phutil_render_tag('a', array('href' => '/maniphest/task/create/?parent=' . $parent_task->getID(), 'class' => 'green button'), 'Create Another Subtask')); $context_bar->appendChild('Created a subtask of <strong>' . $handles[$parent_task->getPHID()]->renderLink() . '</strong>'); } else { if ($workflow == 'create') { $context_bar = new AphrontContextBarView(); $context_bar->addButton('<label>Create Another:</label>'); $context_bar->addButton(phutil_render_tag('a', array('href' => '/maniphest/task/create/?template=' . $task->getID(), 'class' => 'green button'), 'Similar Task')); $context_bar->addButton(phutil_render_tag('a', array('href' => '/maniphest/task/create/', 'class' => 'green button'), 'Empty Task')); $context_bar->appendChild('New task created.'); } } $actions = array(); $action = new AphrontHeadsupActionView(); $action->setName('Edit Task'); $action->setURI('/maniphest/task/edit/' . $task->getID() . '/'); $action->setClass('action-edit'); $actions[] = $action; require_celerity_resource('phabricator-flag-css'); $flag = PhabricatorFlagQuery::loadUserFlag($user, $task->getPHID()); if ($flag) { $class = PhabricatorFlagColor::getCSSClass($flag->getColor()); $color = PhabricatorFlagColor::getColorName($flag->getColor()); $action = new AphrontHeadsupActionView(); $action->setClass('flag-clear ' . $class); $action->setURI('/flag/delete/' . $flag->getID() . '/'); $action->setName('Remove ' . $color . ' Flag'); $action->setWorkflow(true); $actions[] = $action; } else { $action = new AphrontHeadsupActionView(); $action->setClass('phabricator-flag-ghost'); $action->setURI('/flag/edit/' . $task->getPHID() . '/'); $action->setName('Flag Task'); $action->setWorkflow(true); $actions[] = $action; } require_celerity_resource('phabricator-object-selector-css'); require_celerity_resource('javelin-behavior-phabricator-object-selector'); $action = new AphrontHeadsupActionView(); $action->setName('Merge Duplicates'); $action->setURI('/search/attach/' . $task->getPHID() . '/TASK/merge/'); $action->setWorkflow(true); $action->setClass('action-merge'); $actions[] = $action; $action = new AphrontHeadsupActionView(); $action->setName('Create Subtask'); $action->setURI('/maniphest/task/create/?parent=' . $task->getID()); $action->setClass('action-branch'); $actions[] = $action; $action = new AphrontHeadsupActionView(); $action->setName('Edit Dependencies'); $action->setURI('/search/attach/' . $task->getPHID() . '/TASK/dependencies/'); $action->setWorkflow(true); $action->setClass('action-dependencies'); $actions[] = $action; $action = new AphrontHeadsupActionView(); $action->setName('Edit Differential Revisions'); $action->setURI('/search/attach/' . $task->getPHID() . '/DREV/'); $action->setWorkflow(true); $action->setClass('action-attach'); $actions[] = $action; $action_list = new AphrontHeadsupActionListView(); $action_list->setActions($actions); $headsup_panel = new AphrontHeadsupView(); $headsup_panel->setObjectName('T' . $task->getID()); $headsup_panel->setHeader($task->getTitle()); $headsup_panel->setActionList($action_list); $headsup_panel->setProperties($dict); $engine = new PhabricatorMarkupEngine(); $engine->setViewer($user); $engine->addObject($task, ManiphestTask::MARKUP_FIELD_DESCRIPTION); foreach ($transactions as $xaction) { if ($xaction->hasComments()) { $engine->addObject($xaction, ManiphestTransaction::MARKUP_FIELD_BODY); } } $engine->process(); $headsup_panel->appendChild('<div class="phabricator-remarkup">' . $engine->getOutput($task, ManiphestTask::MARKUP_FIELD_DESCRIPTION) . '</div>'); $transaction_types = ManiphestTransactionType::getTransactionTypeMap(); $resolution_types = ManiphestTaskStatus::getTaskStatusMap(); if ($task->getStatus() == ManiphestTaskStatus::STATUS_OPEN) { $resolution_types = array_select_keys($resolution_types, array(ManiphestTaskStatus::STATUS_CLOSED_RESOLVED, ManiphestTaskStatus::STATUS_CLOSED_WONTFIX, ManiphestTaskStatus::STATUS_CLOSED_INVALID, ManiphestTaskStatus::STATUS_CLOSED_SPITE)); } else { $resolution_types = array(ManiphestTaskStatus::STATUS_OPEN => 'Reopened'); $transaction_types[ManiphestTransactionType::TYPE_STATUS] = 'Reopen Task'; unset($transaction_types[ManiphestTransactionType::TYPE_PRIORITY]); unset($transaction_types[ManiphestTransactionType::TYPE_OWNER]); } $default_claim = array($user->getPHID() => $user->getUsername() . ' (' . $user->getRealName() . ')'); $draft = id(new PhabricatorDraft())->loadOneWhere('authorPHID = %s AND draftKey = %s', $user->getPHID(), $task->getPHID()); if ($draft) { $draft_text = $draft->getDraft(); } else { $draft_text = null; } $is_serious = PhabricatorEnv::getEnvConfig('phabricator.serious-business'); if ($is_serious) { // Prevent tasks from being closed "out of spite" in serious business // installs. unset($resolution_types[ManiphestTaskStatus::STATUS_CLOSED_SPITE]); } $comment_form = new AphrontFormView(); $comment_form->setUser($user)->setAction('/maniphest/transaction/save/')->setEncType('multipart/form-data')->addHiddenInput('taskID', $task->getID())->appendChild(id(new AphrontFormSelectControl())->setLabel('Action')->setName('action')->setOptions($transaction_types)->setID('transaction-action'))->appendChild(id(new AphrontFormSelectControl())->setLabel('Resolution')->setName('resolution')->setControlID('resolution')->setControlStyle('display: none')->setOptions($resolution_types))->appendChild(id(new AphrontFormTokenizerControl())->setLabel('Assign To')->setName('assign_to')->setControlID('assign_to')->setControlStyle('display: none')->setID('assign-tokenizer')->setDisableBehavior(true))->appendChild(id(new AphrontFormTokenizerControl())->setLabel('CCs')->setName('ccs')->setControlID('ccs')->setControlStyle('display: none')->setID('cc-tokenizer')->setDisableBehavior(true))->appendChild(id(new AphrontFormSelectControl())->setLabel('Priority')->setName('priority')->setOptions($priority_map)->setControlID('priority')->setControlStyle('display: none')->setValue($task->getPriority()))->appendChild(id(new AphrontFormTokenizerControl())->setLabel('Projects')->setName('projects')->setControlID('projects')->setControlStyle('display: none')->setID('projects-tokenizer')->setDisableBehavior(true))->appendChild(id(new AphrontFormFileControl())->setLabel('File')->setName('file')->setControlID('file')->setControlStyle('display: none'))->appendChild(id(new PhabricatorRemarkupControl())->setLabel('Comments')->setName('comments')->setValue($draft_text)->setID('transaction-comments'))->appendChild(id(new AphrontFormDragAndDropUploadControl())->setLabel('Attached Files')->setName('files')->setActivatedClass('aphront-panel-view-drag-and-drop'))->appendChild(id(new AphrontFormSubmitControl())->setValue($is_serious ? 'Submit' : 'Avast!')); $control_map = array(ManiphestTransactionType::TYPE_STATUS => 'resolution', ManiphestTransactionType::TYPE_OWNER => 'assign_to', ManiphestTransactionType::TYPE_CCS => 'ccs', ManiphestTransactionType::TYPE_PRIORITY => 'priority', ManiphestTransactionType::TYPE_PROJECTS => 'projects', ManiphestTransactionType::TYPE_ATTACH => 'file'); $tokenizer_map = array(ManiphestTransactionType::TYPE_PROJECTS => array('id' => 'projects-tokenizer', 'src' => '/typeahead/common/projects/', 'ondemand' => PhabricatorEnv::getEnvConfig('tokenizer.ondemand'), 'placeholder' => 'Type a project name...'), ManiphestTransactionType::TYPE_OWNER => array('id' => 'assign-tokenizer', 'src' => '/typeahead/common/users/', 'value' => $default_claim, 'limit' => 1, 'ondemand' => PhabricatorEnv::getEnvConfig('tokenizer.ondemand'), 'placeholder' => 'Type a user name...'), ManiphestTransactionType::TYPE_CCS => array('id' => 'cc-tokenizer', 'src' => '/typeahead/common/mailable/', 'ondemand' => PhabricatorEnv::getEnvConfig('tokenizer.ondemand'), 'placeholder' => 'Type a user or mailing list...')); Javelin::initBehavior('maniphest-transaction-controls', array('select' => 'transaction-action', 'controlMap' => $control_map, 'tokenizers' => $tokenizer_map)); Javelin::initBehavior('maniphest-transaction-preview', array('uri' => '/maniphest/transaction/preview/' . $task->getID() . '/', 'preview' => 'transaction-preview', 'comments' => 'transaction-comments', 'action' => 'transaction-action', 'map' => $control_map, 'tokenizers' => $tokenizer_map)); $comment_panel = new AphrontPanelView(); $comment_panel->appendChild($comment_form); $comment_panel->addClass('aphront-panel-accent'); $comment_panel->setHeader($is_serious ? 'Add Comment' : 'Weigh In'); $preview_panel = '<div class="aphront-panel-preview"> <div id="transaction-preview"> <div class="aphront-panel-preview-loading-text"> Loading preview... </div> </div> </div>'; $transaction_view = new ManiphestTransactionListView(); $transaction_view->setTransactions($transactions); $transaction_view->setHandles($handles); $transaction_view->setUser($user); $transaction_view->setAuxiliaryFields($aux_fields); $transaction_view->setMarkupEngine($engine); PhabricatorFeedStoryNotification::updateObjectNotificationViews($user, $task->getPHID()); return $this->buildStandardPageResponse(array($context_bar, $headsup_panel, $transaction_view, $comment_panel, $preview_panel), array('title' => 'T' . $task->getID() . ' ' . $task->getTitle(), 'pageObjects' => array($task->getPHID()))); }