Bring Javelin into Phabricator via git submodule, not copy-and-paste
Summary: Javelin is currently embedded in Phabricator via copy-and-paste of prebuilt packages. This is not so great. Pull it in as a submodule instead and make all the Phabriator resources declare proper dependency trees. Add Javelin linting. Test Plan: I tried to run through pretty much all the JS functionality on the site. This is still a high-risk change, but I did a pretty thorough test Differential: inline comments, revealing diffs, list tokenizers, comment preview, editing/deleting comments, add review action. Maniphest: list tokenizer, comment actions Herald: rule editing, tokenizers, add/remove rows Reviewed By: tomo Reviewers: aran, tomo, mroch, jungejason, tuomaspelkonen CC: aran, tomo, epriestley Differential Revision: 223
This commit is contained in:
		@@ -1,7 +1,7 @@
 | 
			
		||||
{
 | 
			
		||||
  "project_id" : "phabricator",
 | 
			
		||||
  "conduit_uri" : "https://secure.phabricator.com/api/",
 | 
			
		||||
  "lint_engine" : "PhutilLintEngine",
 | 
			
		||||
  "lint_engine" : "PhabricatorLintEngine",
 | 
			
		||||
  "unit_engine" : "PhutilUnitTestEngine",
 | 
			
		||||
  "copyright_holder" : "Facebook, Inc.",
 | 
			
		||||
  "remote_hooks_installed" : true,
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										3
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										3
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,3 @@
 | 
			
		||||
[submodule "externals/javelin"]
 | 
			
		||||
	path = externals/javelin
 | 
			
		||||
	url = git://github.com/epriestley/javelin.git
 | 
			
		||||
							
								
								
									
										1
									
								
								externals/javelin
									
									
									
									
										vendored
									
									
										Submodule
									
								
							
							
								
								
								
								
								
							
						
						
									
										1
									
								
								externals/javelin
									
									
									
									
										vendored
									
									
										Submodule
									
								
							 Submodule externals/javelin added at 099162f62b
									
								
							@@ -2,6 +2,32 @@
 | 
			
		||||
<?php
 | 
			
		||||
 | 
			
		||||
$package_spec = array(
 | 
			
		||||
  'javelin.pkg.js' => array(
 | 
			
		||||
    'javelin-util',
 | 
			
		||||
    'javelin-install',
 | 
			
		||||
    'javelin-event',
 | 
			
		||||
    'javelin-stratcom',
 | 
			
		||||
    'javelin-behavior',
 | 
			
		||||
    'javelin-request',
 | 
			
		||||
    'javelin-vector',
 | 
			
		||||
    'javelin-dom',
 | 
			
		||||
    'javelin-json',
 | 
			
		||||
    'javelin-uri',
 | 
			
		||||
  ),
 | 
			
		||||
  'typeahead.pkg.js' => array(
 | 
			
		||||
    'javelin-typeahead',
 | 
			
		||||
    'javelin-typeahead-normalizer',
 | 
			
		||||
    'javelin-typeahead-source',
 | 
			
		||||
    'javelin-typeahead-preloaded-source',
 | 
			
		||||
    'javelin-typeahead-ondemand-source',
 | 
			
		||||
    'javelin-tokenizer',
 | 
			
		||||
    'javelin-behavior-aphront-basic-tokenizer',
 | 
			
		||||
  ),
 | 
			
		||||
  'workflow.pkg.js' => array(
 | 
			
		||||
    'javelin-mask',
 | 
			
		||||
    'javelin-workflow',
 | 
			
		||||
    'javelin-behavior-workflow',
 | 
			
		||||
  ),
 | 
			
		||||
  'core.pkg.css' => array(
 | 
			
		||||
    'phabricator-core-css',
 | 
			
		||||
    'phabricator-core-buttons-css',
 | 
			
		||||
@@ -14,6 +40,7 @@ $package_spec = array(
 | 
			
		||||
    'aphront-crumbs-view-css',
 | 
			
		||||
    'aphront-tokenizer-control-css',
 | 
			
		||||
    'aphront-typeahead-control-css',
 | 
			
		||||
    'aphront-list-filter-view-css',
 | 
			
		||||
 | 
			
		||||
    'phabricator-directory-css',
 | 
			
		||||
 | 
			
		||||
@@ -63,6 +90,7 @@ $files = id(new FileFinder($root))
 | 
			
		||||
  ->withType('f')
 | 
			
		||||
  ->withSuffix('js')
 | 
			
		||||
  ->withSuffix('css')
 | 
			
		||||
  ->withFollowSymlinks(true)
 | 
			
		||||
  ->setGenerateChecksums(true)
 | 
			
		||||
  ->find();
 | 
			
		||||
 | 
			
		||||
@@ -101,9 +129,10 @@ foreach ($file_map as $path => $info) {
 | 
			
		||||
  $provides = array_filter($provides);
 | 
			
		||||
  $requires = array_filter($requires);
 | 
			
		||||
 | 
			
		||||
  if (count($provides) !== 1) {
 | 
			
		||||
  if (count($provides) > 1) {
 | 
			
		||||
    // NOTE: Documentation-only JS is permitted to @provide no targets.
 | 
			
		||||
    throw new Exception(
 | 
			
		||||
      "File {$path} must @provide exactly one Celerity target.");
 | 
			
		||||
      "File {$path} must @provide at most one Celerity target.");
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  $provides = reset($provides);
 | 
			
		||||
 
 | 
			
		||||
@@ -235,14 +235,19 @@ celerity_register_resource_map(array(
 | 
			
		||||
  ),
 | 
			
		||||
  'herald-rule-editor' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/ec8e2110/rsrc/js/application/herald/HeraldRuleEditor.js',
 | 
			
		||||
    'uri' => '/res/f3122b0a/rsrc/js/application/herald/HeraldRuleEditor.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'multirow-row-manager',
 | 
			
		||||
      1 => 'javelin-lib-dev',
 | 
			
		||||
      2 => 'javelin-typeahead-dev',
 | 
			
		||||
      3 => 'path-typeahead',
 | 
			
		||||
      1 => 'javelin-install',
 | 
			
		||||
      2 => 'javelin-typeahead',
 | 
			
		||||
      3 => 'javelin-util',
 | 
			
		||||
      4 => 'javelin-dom',
 | 
			
		||||
      5 => 'javelin-tokenizer',
 | 
			
		||||
      6 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
      7 => 'javelin-stratcom',
 | 
			
		||||
      8 => 'javelin-json',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/herald/HeraldRuleEditor.js',
 | 
			
		||||
  ),
 | 
			
		||||
@@ -255,248 +260,463 @@ celerity_register_resource_map(array(
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/css/application/herald/herald-test.css',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-aphront-basic-tokenizer' =>
 | 
			
		||||
  'javelin-behavior' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/8317d761/rsrc/js/application/core/behavior-tokenizer.js',
 | 
			
		||||
    'uri' => '/res/dc576a49/rsrc/js/javelin/lib/behavior.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/behavior.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-aphront-basic-tokenizer' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/d48d2732/rsrc/js/application/core/behavior-tokenizer.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-typeahead',
 | 
			
		||||
      2 => 'javelin-tokenizer',
 | 
			
		||||
      3 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
      4 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/behavior-tokenizer.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-dark-console' =>
 | 
			
		||||
  0 =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/020b0265/rsrc/js/application/core/behavior-dark-console.js',
 | 
			
		||||
    'uri' => '/res/e3d992aa/rsrc/js/javelin/docs/Base.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/docs/Base.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-dark-console' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/447bd50a/rsrc/js/application/core/behavior-dark-console.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-dom',
 | 
			
		||||
      4 => 'javelin-request',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/behavior-dark-console.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-add-reviewers' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/330154e4/rsrc/js/application/differential/behavior-add-reviewers.js',
 | 
			
		||||
    'uri' => '/res/fa2f29c4/rsrc/js/application/differential/behavior-add-reviewers.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-tokenizer',
 | 
			
		||||
      3 => 'javelin-typeahead',
 | 
			
		||||
      4 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-add-reviewers.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-diff-radios' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/fdeb3823/rsrc/js/application/differential/behavior-diff-radios.js',
 | 
			
		||||
    'uri' => '/res/d3365dba/rsrc/js/application/differential/behavior-diff-radios.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-diff-radios.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-edit-inline-comments' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/6a6f38e6/rsrc/js/application/differential/behavior-edit-inline-comments.js',
 | 
			
		||||
    'uri' => '/res/f18ee6ae/rsrc/js/application/differential/behavior-edit-inline-comments.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-workflow',
 | 
			
		||||
      4 => 'javelin-vector',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-edit-inline-comments.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-feedback-preview' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/8695d8b8/rsrc/js/application/differential/behavior-comment-preview.js',
 | 
			
		||||
    'uri' => '/res/139c85b8/rsrc/js/application/differential/behavior-comment-preview.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-request',
 | 
			
		||||
      4 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-comment-preview.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-populate' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/a13dcd7e/rsrc/js/application/differential/behavior-populate.js',
 | 
			
		||||
    'uri' => '/res/d4d4fd9d/rsrc/js/application/differential/behavior-populate.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-request',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-populate.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-show-all-comments' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/2a3592b8/rsrc/js/application/differential/behavior-show-all-comments.js',
 | 
			
		||||
    'uri' => '/res/4d34a1e7/rsrc/js/application/differential/behavior-show-all-comments.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-show-all-comments.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-differential-show-more' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/ea998002/rsrc/js/application/differential/behavior-show-more.js',
 | 
			
		||||
    'uri' => '/res/6af8c5bb/rsrc/js/application/differential/behavior-show-more.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-request',
 | 
			
		||||
      3 => 'javelin-util',
 | 
			
		||||
      4 => 'javelin-stratcom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/differential/behavior-show-more.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-diffusion-jump-to' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/4f3f6cdc/rsrc/js/application/diffusion/behavior-jump-to.js',
 | 
			
		||||
    'uri' => '/res/2a8ca30b/rsrc/js/application/diffusion/behavior-jump-to.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
      2 => 'javelin-vector',
 | 
			
		||||
      3 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/diffusion/behavior-jump-to.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-diffusion-pull-lastmodified' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/6a5e7374/rsrc/js/application/diffusion/behavior-pull-lastmodified.js',
 | 
			
		||||
    'uri' => '/res/f3e3f3a6/rsrc/js/application/diffusion/behavior-pull-lastmodified.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-request',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/diffusion/behavior-pull-lastmodified.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-error-log' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/c57a323f/rsrc/js/application/core/behavior-error-log.js',
 | 
			
		||||
    'uri' => '/res/ad4e82d4/rsrc/js/application/core/behavior-error-log.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/behavior-error-log.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-herald-rule-editor' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/48108130/rsrc/js/application/herald/herald-rule-editor.js',
 | 
			
		||||
    'uri' => '/res/f18bcd5e/rsrc/js/application/herald/herald-rule-editor.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'herald-rule-editor',
 | 
			
		||||
      1 => 'javelin-lib-dev',
 | 
			
		||||
      1 => 'javelin-behavior',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/herald/herald-rule-editor.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-maniphest-transaction-controls' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/fc6a8722/rsrc/js/application/maniphest/behavior-transaction-controls.js',
 | 
			
		||||
    'uri' => '/res/f2eae88a/rsrc/js/application/maniphest/behavior-transaction-controls.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-tokenizer',
 | 
			
		||||
      3 => 'javelin-typeahead',
 | 
			
		||||
      4 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/maniphest/behavior-transaction-controls.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-owners-path-editor' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/7568aa22/rsrc/js/application/owners/owners-path-editor.js',
 | 
			
		||||
    'uri' => '/res/b379a0d4/rsrc/js/application/owners/owners-path-editor.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'owners-path-editor',
 | 
			
		||||
      1 => 'javelin-lib-dev',
 | 
			
		||||
      1 => 'javelin-behavior',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/owners/owners-path-editor.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-phabricator-object-selector' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/85d0769b/rsrc/js/application/core/behavior-object-selector.js',
 | 
			
		||||
    'uri' => '/res/e899a55e/rsrc/js/application/core/behavior-object-selector.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-request',
 | 
			
		||||
      3 => 'javelin-util',
 | 
			
		||||
      4 => 'javelin-stratcom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/behavior-object-selector.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-behavior-workflow' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/15446e7e/rsrc/js/application/core/behavior-workflow.js',
 | 
			
		||||
    'uri' => '/res/b5bc59cb/rsrc/js/application/core/behavior-workflow.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-behavior',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-workflow',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/behavior-workflow.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-init-prod' =>
 | 
			
		||||
  'javelin-dom' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/1267c868/rsrc/js/javelin/init.min.js',
 | 
			
		||||
    'uri' => '/res/21c1392d/rsrc/js/javelin/lib/DOM.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
      2 => 'javelin-vector',
 | 
			
		||||
      3 => 'javelin-stratcom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/init.min.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/DOM.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-lib-dev' =>
 | 
			
		||||
  'javelin-event' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/a0e7a5e9/rsrc/js/javelin/javelin.dev.js',
 | 
			
		||||
    'uri' => '/res/807b95e6/rsrc/js/javelin/core/Event.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/javelin.dev.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/core/Event.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-lib-prod' =>
 | 
			
		||||
  'javelin-install' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/2f2b3b2e/rsrc/js/javelin/javelin.min.js',
 | 
			
		||||
    'uri' => '/res/c11fe5b3/rsrc/js/javelin/core/install.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/javelin.min.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/core/install.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-json' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/62c8cc8d/rsrc/js/javelin/lib/JSON.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/JSON.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-magical-init' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/76614f84/rsrc/js/javelin/init.dev.js',
 | 
			
		||||
    'uri' => '/res/6d53e259/rsrc/js/javelin/core/init.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/init.dev.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/core/init.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-dev' =>
 | 
			
		||||
  'javelin-mask' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/6de6ae59/rsrc/js/javelin/typeahead.dev.js',
 | 
			
		||||
    'uri' => '/res/ba2f665a/rsrc/js/javelin/lib/Mask.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-vector',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/typeahead.dev.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/Mask.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-prod' =>
 | 
			
		||||
  'javelin-request' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/69d5fad1/rsrc/js/javelin/typeahead.min.js',
 | 
			
		||||
    'uri' => '/res/3947083d/rsrc/js/javelin/lib/Request.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-behavior',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/typeahead.min.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/Request.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-workflow-dev' =>
 | 
			
		||||
  'javelin-stratcom' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/c6b17f93/rsrc/js/javelin/workflow.dev.js',
 | 
			
		||||
    'uri' => '/res/3421b115/rsrc/js/javelin/core/Stratcom.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-event',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-magical-init',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/workflow.dev.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/core/Stratcom.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-workflow-prod' =>
 | 
			
		||||
  'javelin-tokenizer' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/b758e0a0/rsrc/js/javelin/workflow.min.js',
 | 
			
		||||
    'uri' => '/res/74fe92c6/rsrc/js/javelin/lib/control/tokenizer/Tokenizer.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-typeahead',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-util',
 | 
			
		||||
      3 => 'javelin-stratcom',
 | 
			
		||||
      4 => 'javelin-vector',
 | 
			
		||||
      5 => 'javelin-install',
 | 
			
		||||
      6 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/workflow.min.js',
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/tokenizer/Tokenizer.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/5a701345/rsrc/js/javelin/lib/control/typeahead/Typeahead.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-dom',
 | 
			
		||||
      2 => 'javelin-vector',
 | 
			
		||||
      3 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/typeahead/Typeahead.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-normalizer' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/8d49e2de/rsrc/js/javelin/lib/control/typeahead/normalizer/TypeaheadNormalizer.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/typeahead/normalizer/TypeaheadNormalizer.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-ondemand-source' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/00b46be8/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadOnDemandSource.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
      2 => 'javelin-stratcom',
 | 
			
		||||
      3 => 'javelin-request',
 | 
			
		||||
      4 => 'javelin-typeahead-source',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadOnDemandSource.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-preloaded-source' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/aefaf410/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadPreloadedSource.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
      2 => 'javelin-stratcom',
 | 
			
		||||
      3 => 'javelin-request',
 | 
			
		||||
      4 => 'javelin-typeahead-source',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadPreloadedSource.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-typeahead-source' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/b1184e7d/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadSource.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-typeahead-normalizer',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/control/typeahead/source/TypeaheadSource.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-uri' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/03448af9/rsrc/js/javelin/lib/URI.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/URI.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-util' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/031851eb/rsrc/js/javelin/core/util.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-magical-init',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/core/util.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-vector' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/184e9d71/rsrc/js/javelin/lib/Vector.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-event',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/Vector.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'javelin-workflow' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/24389bc8/rsrc/js/javelin/lib/Workflow.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-stratcom',
 | 
			
		||||
      1 => 'javelin-request',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-vector',
 | 
			
		||||
      4 => 'javelin-install',
 | 
			
		||||
      5 => 'javelin-util',
 | 
			
		||||
      6 => 'javelin-mask',
 | 
			
		||||
      7 => 'javelin-uri',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/javelin/lib/Workflow.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'mainphest-task-detail-css' =>
 | 
			
		||||
  array(
 | 
			
		||||
@@ -527,24 +747,28 @@ celerity_register_resource_map(array(
 | 
			
		||||
  ),
 | 
			
		||||
  'multirow-row-manager' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/330d076b/rsrc/js/application/core/MultirowRowManager.js',
 | 
			
		||||
    'uri' => '/res/cae26c67/rsrc/js/application/core/MultirowRowManager.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-stratcom',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/core/MultirowRowManager.js',
 | 
			
		||||
  ),
 | 
			
		||||
  'owners-path-editor' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/b01c1ca9/rsrc/js/application/owners/OwnersPathEditor.js',
 | 
			
		||||
    'uri' => '/res/003f3d3f/rsrc/js/application/owners/OwnersPathEditor.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'multirow-row-manager',
 | 
			
		||||
      1 => 'javelin-lib-dev',
 | 
			
		||||
      2 => 'javelin-typeahead-dev',
 | 
			
		||||
      3 => 'path-typeahead',
 | 
			
		||||
      1 => 'javelin-install',
 | 
			
		||||
      2 => 'path-typeahead',
 | 
			
		||||
      3 => 'javelin-dom',
 | 
			
		||||
      4 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/owners/OwnersPathEditor.js',
 | 
			
		||||
  ),
 | 
			
		||||
@@ -559,12 +783,16 @@ celerity_register_resource_map(array(
 | 
			
		||||
  ),
 | 
			
		||||
  'path-typeahead' =>
 | 
			
		||||
  array(
 | 
			
		||||
    'uri' => '/res/42fb76c3/rsrc/js/application/herald/PathTypeahead.js',
 | 
			
		||||
    'uri' => '/res/594d2576/rsrc/js/application/herald/PathTypeahead.js',
 | 
			
		||||
    'type' => 'js',
 | 
			
		||||
    'requires' =>
 | 
			
		||||
    array(
 | 
			
		||||
      0 => 'javelin-lib-dev',
 | 
			
		||||
      1 => 'javelin-typeahead-dev',
 | 
			
		||||
      0 => 'javelin-install',
 | 
			
		||||
      1 => 'javelin-typeahead',
 | 
			
		||||
      2 => 'javelin-dom',
 | 
			
		||||
      3 => 'javelin-request',
 | 
			
		||||
      4 => 'javelin-typeahead-ondemand-source',
 | 
			
		||||
      5 => 'javelin-util',
 | 
			
		||||
    ),
 | 
			
		||||
    'disk' => '/rsrc/js/application/herald/PathTypeahead.js',
 | 
			
		||||
  ),
 | 
			
		||||
@@ -653,30 +881,7 @@ celerity_register_resource_map(array(
 | 
			
		||||
), array (
 | 
			
		||||
  'packages' =>
 | 
			
		||||
  array (
 | 
			
		||||
    '4270730a' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'core.pkg.css',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
      array (
 | 
			
		||||
        0 => 'phabricator-core-css',
 | 
			
		||||
        1 => 'phabricator-core-buttons-css',
 | 
			
		||||
        2 => 'phabricator-standard-page-view',
 | 
			
		||||
        3 => 'aphront-dialog-view-css',
 | 
			
		||||
        4 => 'aphront-form-view-css',
 | 
			
		||||
        5 => 'aphront-panel-view-css',
 | 
			
		||||
        6 => 'aphront-side-nav-view-css',
 | 
			
		||||
        7 => 'aphront-table-view-css',
 | 
			
		||||
        8 => 'aphront-crumbs-view-css',
 | 
			
		||||
        9 => 'aphront-tokenizer-control-css',
 | 
			
		||||
        10 => 'aphront-typeahead-control-css',
 | 
			
		||||
        11 => 'phabricator-directory-css',
 | 
			
		||||
        12 => 'phabricator-remarkup-css',
 | 
			
		||||
        13 => 'syntax-highlighting-css',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/4270730a/core.pkg.css',
 | 
			
		||||
      'type' => 'css',
 | 
			
		||||
    ),
 | 
			
		||||
    '6c786373' =>
 | 
			
		||||
    '3b698834' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'differential.pkg.js',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
@@ -687,7 +892,19 @@ celerity_register_resource_map(array(
 | 
			
		||||
        3 => 'javelin-behavior-differential-show-more',
 | 
			
		||||
        4 => 'javelin-behavior-differential-diff-radios',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/6c786373/differential.pkg.js',
 | 
			
		||||
      'uri' => '/res/pkg/3b698834/differential.pkg.js',
 | 
			
		||||
      'type' => 'js',
 | 
			
		||||
    ),
 | 
			
		||||
    '71a78877' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'workflow.pkg.js',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
      array (
 | 
			
		||||
        0 => 'javelin-mask',
 | 
			
		||||
        1 => 'javelin-workflow',
 | 
			
		||||
        2 => 'javelin-behavior-workflow',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/71a78877/workflow.pkg.js',
 | 
			
		||||
      'type' => 'js',
 | 
			
		||||
    ),
 | 
			
		||||
    '8e4ef51b' =>
 | 
			
		||||
@@ -707,6 +924,46 @@ celerity_register_resource_map(array(
 | 
			
		||||
      'uri' => '/res/pkg/8e4ef51b/differential.pkg.css',
 | 
			
		||||
      'type' => 'css',
 | 
			
		||||
    ),
 | 
			
		||||
    'a44a7841' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'typeahead.pkg.js',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
      array (
 | 
			
		||||
        0 => 'javelin-typeahead',
 | 
			
		||||
        1 => 'javelin-typeahead-normalizer',
 | 
			
		||||
        2 => 'javelin-typeahead-source',
 | 
			
		||||
        3 => 'javelin-typeahead-preloaded-source',
 | 
			
		||||
        4 => 'javelin-typeahead-ondemand-source',
 | 
			
		||||
        5 => 'javelin-tokenizer',
 | 
			
		||||
        6 => 'javelin-behavior-aphront-basic-tokenizer',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/a44a7841/typeahead.pkg.js',
 | 
			
		||||
      'type' => 'js',
 | 
			
		||||
    ),
 | 
			
		||||
    'c4276ad7' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'core.pkg.css',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
      array (
 | 
			
		||||
        0 => 'phabricator-core-css',
 | 
			
		||||
        1 => 'phabricator-core-buttons-css',
 | 
			
		||||
        2 => 'phabricator-standard-page-view',
 | 
			
		||||
        3 => 'aphront-dialog-view-css',
 | 
			
		||||
        4 => 'aphront-form-view-css',
 | 
			
		||||
        5 => 'aphront-panel-view-css',
 | 
			
		||||
        6 => 'aphront-side-nav-view-css',
 | 
			
		||||
        7 => 'aphront-table-view-css',
 | 
			
		||||
        8 => 'aphront-crumbs-view-css',
 | 
			
		||||
        9 => 'aphront-tokenizer-control-css',
 | 
			
		||||
        10 => 'aphront-typeahead-control-css',
 | 
			
		||||
        11 => 'aphront-list-filter-view-css',
 | 
			
		||||
        12 => 'phabricator-directory-css',
 | 
			
		||||
        13 => 'phabricator-remarkup-css',
 | 
			
		||||
        14 => 'syntax-highlighting-css',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/c4276ad7/core.pkg.css',
 | 
			
		||||
      'type' => 'css',
 | 
			
		||||
    ),
 | 
			
		||||
    'eadf6ec3' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'diffusion.pkg.css',
 | 
			
		||||
@@ -717,17 +974,37 @@ celerity_register_resource_map(array(
 | 
			
		||||
      'uri' => '/res/pkg/eadf6ec3/diffusion.pkg.css',
 | 
			
		||||
      'type' => 'css',
 | 
			
		||||
    ),
 | 
			
		||||
    'fc6ed8bc' =>
 | 
			
		||||
    array (
 | 
			
		||||
      'name' => 'javelin.pkg.js',
 | 
			
		||||
      'symbols' =>
 | 
			
		||||
      array (
 | 
			
		||||
        0 => 'javelin-util',
 | 
			
		||||
        1 => 'javelin-install',
 | 
			
		||||
        2 => 'javelin-event',
 | 
			
		||||
        3 => 'javelin-stratcom',
 | 
			
		||||
        4 => 'javelin-behavior',
 | 
			
		||||
        5 => 'javelin-request',
 | 
			
		||||
        6 => 'javelin-vector',
 | 
			
		||||
        7 => 'javelin-dom',
 | 
			
		||||
        8 => 'javelin-json',
 | 
			
		||||
        9 => 'javelin-uri',
 | 
			
		||||
      ),
 | 
			
		||||
      'uri' => '/res/pkg/fc6ed8bc/javelin.pkg.js',
 | 
			
		||||
      'type' => 'js',
 | 
			
		||||
    ),
 | 
			
		||||
  ),
 | 
			
		||||
  'reverse' =>
 | 
			
		||||
  array (
 | 
			
		||||
    'aphront-crumbs-view-css' => '4270730a',
 | 
			
		||||
    'aphront-dialog-view-css' => '4270730a',
 | 
			
		||||
    'aphront-form-view-css' => '4270730a',
 | 
			
		||||
    'aphront-panel-view-css' => '4270730a',
 | 
			
		||||
    'aphront-side-nav-view-css' => '4270730a',
 | 
			
		||||
    'aphront-table-view-css' => '4270730a',
 | 
			
		||||
    'aphront-tokenizer-control-css' => '4270730a',
 | 
			
		||||
    'aphront-typeahead-control-css' => '4270730a',
 | 
			
		||||
    'aphront-crumbs-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-dialog-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-form-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-list-filter-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-panel-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-side-nav-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-table-view-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-tokenizer-control-css' => 'c4276ad7',
 | 
			
		||||
    'aphront-typeahead-control-css' => 'c4276ad7',
 | 
			
		||||
    'differential-changeset-view-css' => '8e4ef51b',
 | 
			
		||||
    'differential-core-view-css' => '8e4ef51b',
 | 
			
		||||
    'differential-revision-add-comment-css' => '8e4ef51b',
 | 
			
		||||
@@ -737,16 +1014,36 @@ celerity_register_resource_map(array(
 | 
			
		||||
    'differential-revision-history-css' => '8e4ef51b',
 | 
			
		||||
    'differential-table-of-contents-css' => '8e4ef51b',
 | 
			
		||||
    'diffusion-commit-view-css' => 'eadf6ec3',
 | 
			
		||||
    'javelin-behavior-differential-diff-radios' => '6c786373',
 | 
			
		||||
    'javelin-behavior-differential-edit-inline-comments' => '6c786373',
 | 
			
		||||
    'javelin-behavior-differential-feedback-preview' => '6c786373',
 | 
			
		||||
    'javelin-behavior-differential-populate' => '6c786373',
 | 
			
		||||
    'javelin-behavior-differential-show-more' => '6c786373',
 | 
			
		||||
    'phabricator-core-buttons-css' => '4270730a',
 | 
			
		||||
    'phabricator-core-css' => '4270730a',
 | 
			
		||||
    'phabricator-directory-css' => '4270730a',
 | 
			
		||||
    'phabricator-remarkup-css' => '4270730a',
 | 
			
		||||
    'phabricator-standard-page-view' => '4270730a',
 | 
			
		||||
    'syntax-highlighting-css' => '4270730a',
 | 
			
		||||
    'javelin-behavior' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-behavior-aphront-basic-tokenizer' => 'a44a7841',
 | 
			
		||||
    'javelin-behavior-differential-diff-radios' => '3b698834',
 | 
			
		||||
    'javelin-behavior-differential-edit-inline-comments' => '3b698834',
 | 
			
		||||
    'javelin-behavior-differential-feedback-preview' => '3b698834',
 | 
			
		||||
    'javelin-behavior-differential-populate' => '3b698834',
 | 
			
		||||
    'javelin-behavior-differential-show-more' => '3b698834',
 | 
			
		||||
    'javelin-behavior-workflow' => '71a78877',
 | 
			
		||||
    'javelin-dom' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-event' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-install' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-json' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-mask' => '71a78877',
 | 
			
		||||
    'javelin-request' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-stratcom' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-tokenizer' => 'a44a7841',
 | 
			
		||||
    'javelin-typeahead' => 'a44a7841',
 | 
			
		||||
    'javelin-typeahead-normalizer' => 'a44a7841',
 | 
			
		||||
    'javelin-typeahead-ondemand-source' => 'a44a7841',
 | 
			
		||||
    'javelin-typeahead-preloaded-source' => 'a44a7841',
 | 
			
		||||
    'javelin-typeahead-source' => 'a44a7841',
 | 
			
		||||
    'javelin-uri' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-util' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-vector' => 'fc6ed8bc',
 | 
			
		||||
    'javelin-workflow' => '71a78877',
 | 
			
		||||
    'phabricator-core-buttons-css' => 'c4276ad7',
 | 
			
		||||
    'phabricator-core-css' => 'c4276ad7',
 | 
			
		||||
    'phabricator-directory-css' => 'c4276ad7',
 | 
			
		||||
    'phabricator-remarkup-css' => 'c4276ad7',
 | 
			
		||||
    'phabricator-standard-page-view' => 'c4276ad7',
 | 
			
		||||
    'syntax-highlighting-css' => 'c4276ad7',
 | 
			
		||||
  ),
 | 
			
		||||
));
 | 
			
		||||
 
 | 
			
		||||
@@ -318,6 +318,8 @@ phutil_register_library_map(array(
 | 
			
		||||
    'PhabricatorFileViewController' => 'applications/files/controller/view',
 | 
			
		||||
    'PhabricatorGoodForNothingWorker' => 'infrastructure/daemon/workers/worker/goodfornothing',
 | 
			
		||||
    'PhabricatorHandleObjectSelectorDataView' => 'applications/phid/handle/view/selector',
 | 
			
		||||
    'PhabricatorJavelinLinter' => 'infrastructure/lint/linter/javelin',
 | 
			
		||||
    'PhabricatorLintEngine' => 'infrastructure/lint/engine',
 | 
			
		||||
    'PhabricatorLiskDAO' => 'applications/base/storage/lisk',
 | 
			
		||||
    'PhabricatorLoginController' => 'applications/auth/controller/login',
 | 
			
		||||
    'PhabricatorLogoutController' => 'applications/auth/controller/logout',
 | 
			
		||||
@@ -731,6 +733,8 @@ phutil_register_library_map(array(
 | 
			
		||||
    'PhabricatorFileUploadController' => 'PhabricatorFileController',
 | 
			
		||||
    'PhabricatorFileViewController' => 'PhabricatorFileController',
 | 
			
		||||
    'PhabricatorGoodForNothingWorker' => 'PhabricatorWorker',
 | 
			
		||||
    'PhabricatorJavelinLinter' => 'ArcanistLinter',
 | 
			
		||||
    'PhabricatorLintEngine' => 'PhutilLintEngine',
 | 
			
		||||
    'PhabricatorLiskDAO' => 'LiskDAO',
 | 
			
		||||
    'PhabricatorLoginController' => 'PhabricatorAuthController',
 | 
			
		||||
    'PhabricatorLogoutController' => 'PhabricatorAuthController',
 | 
			
		||||
 
 | 
			
		||||
@@ -21,6 +21,7 @@ final class CelerityResourceMap {
 | 
			
		||||
  private static $instance;
 | 
			
		||||
  private $resourceMap;
 | 
			
		||||
  private $packageMap;
 | 
			
		||||
  private $reverseMap;
 | 
			
		||||
 | 
			
		||||
  public static function getInstance() {
 | 
			
		||||
    if (empty(self::$instance)) {
 | 
			
		||||
@@ -107,6 +108,21 @@ final class CelerityResourceMap {
 | 
			
		||||
    return $paths;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function lookupSymbolInformation($symbol) {
 | 
			
		||||
    return idx($this->resourceMap, $symbol);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function lookupFileInformation($path) {
 | 
			
		||||
    if (empty($this->reverseMap)) {
 | 
			
		||||
      $this->reverseMap = array();
 | 
			
		||||
      foreach ($this->resourceMap as $symbol => $data) {
 | 
			
		||||
        $data['provides'] = $symbol;
 | 
			
		||||
        $this->reverseMap[$data['disk']] = $data;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
    return idx($this->reverseMap, $path);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function celerity_register_resource_map(array $map, array $package_map) {
 | 
			
		||||
 
 | 
			
		||||
@@ -25,6 +25,7 @@ final class CelerityStaticResourceResponse {
 | 
			
		||||
  private $metadata = array();
 | 
			
		||||
  private $metadataBlock = 0;
 | 
			
		||||
  private $behaviors = array();
 | 
			
		||||
  private $hasRendered = array();
 | 
			
		||||
 | 
			
		||||
  public function __construct() {
 | 
			
		||||
    if (isset($_REQUEST['__metablock__'])) {
 | 
			
		||||
@@ -64,14 +65,36 @@ final class CelerityStaticResourceResponse {
 | 
			
		||||
    return $this;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function renderSingleResource($symbol) {
 | 
			
		||||
    $map = CelerityResourceMap::getInstance();
 | 
			
		||||
    $resolved = $map->resolveResources(array($symbol));
 | 
			
		||||
    $packaged = $map->packageResources($resolved);
 | 
			
		||||
    return $this->renderPackagedResources($packaged);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function renderResourcesOfType($type) {
 | 
			
		||||
    $this->resolveResources();
 | 
			
		||||
    $output = array();
 | 
			
		||||
 | 
			
		||||
    $resources = array();
 | 
			
		||||
    foreach ($this->packaged as $resource) {
 | 
			
		||||
      if ($resource['type'] == $type) {
 | 
			
		||||
        $output[] = $this->renderResource($resource);
 | 
			
		||||
        $resources[] = $resource;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return $this->renderPackagedResources($resources);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private function renderPackagedResources(array $resources) {
 | 
			
		||||
    $output = array();
 | 
			
		||||
    foreach ($resources as $resource) {
 | 
			
		||||
      if (isset($this->hasRendered[$resource['uri']])) {
 | 
			
		||||
        continue;
 | 
			
		||||
      }
 | 
			
		||||
      $this->hasRendered[$resource['uri']] = true;
 | 
			
		||||
 | 
			
		||||
      $output[] = $this->renderResource($resource);
 | 
			
		||||
    }
 | 
			
		||||
    return implode("\n", $output);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										45
									
								
								src/infrastructure/lint/engine/PhabricatorLintEngine.php
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										45
									
								
								src/infrastructure/lint/engine/PhabricatorLintEngine.php
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,45 @@
 | 
			
		||||
<?php
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright 2011 Facebook, Inc.
 | 
			
		||||
 *
 | 
			
		||||
 * Licensed under the Apache License, Version 2.0 (the "License");
 | 
			
		||||
 * you may not use this file except in compliance with the License.
 | 
			
		||||
 * You may obtain a copy of the License at
 | 
			
		||||
 *
 | 
			
		||||
 *   http://www.apache.org/licenses/LICENSE-2.0
 | 
			
		||||
 *
 | 
			
		||||
 * Unless required by applicable law or agreed to in writing, software
 | 
			
		||||
 * distributed under the License is distributed on an "AS IS" BASIS,
 | 
			
		||||
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 | 
			
		||||
 * See the License for the specific language governing permissions and
 | 
			
		||||
 * limitations under the License.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
class PhabricatorLintEngine extends PhutilLintEngine {
 | 
			
		||||
 | 
			
		||||
  public function buildLinters() {
 | 
			
		||||
    $linters = parent::buildLinters();
 | 
			
		||||
 | 
			
		||||
    $paths = $this->getPaths();
 | 
			
		||||
 | 
			
		||||
    foreach ($paths as $key => $path) {
 | 
			
		||||
      if (!$this->pathExists($path)) {
 | 
			
		||||
        unset($paths[$key]);
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    $javelin_linter = new PhabricatorJavelinLinter();
 | 
			
		||||
    $linters[] = $javelin_linter;
 | 
			
		||||
 | 
			
		||||
    foreach ($paths as $path) {
 | 
			
		||||
      if (preg_match('/\.js$/', $path)) {
 | 
			
		||||
        $javelin_linter->addPath($path);
 | 
			
		||||
        $javelin_linter->addData($path, $this->loadData($path));
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return $linters;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										14
									
								
								src/infrastructure/lint/engine/__init__.php
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										14
									
								
								src/infrastructure/lint/engine/__init__.php
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,14 @@
 | 
			
		||||
<?php
 | 
			
		||||
/**
 | 
			
		||||
 * This file is automatically generated. Lint this module to rebuild it.
 | 
			
		||||
 * @generated
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
phutil_require_module('arcanist', 'lint/engine/phutil');
 | 
			
		||||
 | 
			
		||||
phutil_require_module('phabricator', 'infrastructure/lint/linter/javelin');
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
phutil_require_source('PhabricatorLintEngine.php');
 | 
			
		||||
@@ -0,0 +1,207 @@
 | 
			
		||||
<?php
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright 2011 Facebook, Inc.
 | 
			
		||||
 *
 | 
			
		||||
 * Licensed under the Apache License, Version 2.0 (the "License");
 | 
			
		||||
 * you may not use this file except in compliance with the License.
 | 
			
		||||
 * You may obtain a copy of the License at
 | 
			
		||||
 *
 | 
			
		||||
 *   http://www.apache.org/licenses/LICENSE-2.0
 | 
			
		||||
 *
 | 
			
		||||
 * Unless required by applicable law or agreed to in writing, software
 | 
			
		||||
 * distributed under the License is distributed on an "AS IS" BASIS,
 | 
			
		||||
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 | 
			
		||||
 * See the License for the specific language governing permissions and
 | 
			
		||||
 * limitations under the License.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
class PhabricatorJavelinLinter extends ArcanistLinter {
 | 
			
		||||
 | 
			
		||||
  private $symbols = array();
 | 
			
		||||
 | 
			
		||||
  const LINT_PRIVATE_ACCESS = 1;
 | 
			
		||||
  const LINT_MISSING_DEPENDENCY = 2;
 | 
			
		||||
  const LINT_UNNECESSARY_DEPENDENCY = 3;
 | 
			
		||||
  const LINT_UNKNOWN_DEPENDENCY = 4;
 | 
			
		||||
 | 
			
		||||
  public function willLintPaths(array $paths) {
 | 
			
		||||
    $futures = array();
 | 
			
		||||
    foreach ($paths as $path) {
 | 
			
		||||
      $future = $this->newSymbolsFuture($path);
 | 
			
		||||
      $futures[$path] = $future;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    foreach (Futures($futures)->limit(8) as $path => $future) {
 | 
			
		||||
      $this->symbols[$path] = $future->resolvex();
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function getLinterName() {
 | 
			
		||||
    return 'JAVELIN';
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function getLintSeverityMap() {
 | 
			
		||||
    return array();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function getLintNameMap() {
 | 
			
		||||
    return array(
 | 
			
		||||
      self::LINT_PRIVATE_ACCESS => 'Private Method/Member Access',
 | 
			
		||||
      self::LINT_MISSING_DEPENDENCY => 'Missing Javelin Dependency',
 | 
			
		||||
      self::LINT_UNNECESSARY_DEPENDENCY => 'Unnecessary Javelin Dependency',
 | 
			
		||||
      self::LINT_UNKNOWN_DEPENDENCY => 'Unknown Javelin Dependency',
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public function lintPath($path) {
 | 
			
		||||
 | 
			
		||||
    list($uses, $installs) = $this->getUsedAndInstalledSymbolsForPath($path);
 | 
			
		||||
    foreach ($uses as $symbol => $line) {
 | 
			
		||||
      $parts = explode('.', $symbol);
 | 
			
		||||
      foreach ($parts as $part) {
 | 
			
		||||
        if ($part[0] == '_' && $part[1] != '_') {
 | 
			
		||||
          $base = implode('.', array_slice($parts, 0, 2));
 | 
			
		||||
          if (!array_key_exists($base, $installs)) {
 | 
			
		||||
            $this->raiseLintAtLine(
 | 
			
		||||
              $line,
 | 
			
		||||
              0,
 | 
			
		||||
              self::LINT_PRIVATE_ACCESS,
 | 
			
		||||
              "This file accesses private symbol '{$symbol}' across file ".
 | 
			
		||||
              "boundaries. You may only access private members and methods ".
 | 
			
		||||
              "from the file where they are defined.");
 | 
			
		||||
          }
 | 
			
		||||
          break;
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if ($this->getEngine()->getCommitHookMode()) {
 | 
			
		||||
      // Don't do the dependency checks in commit-hook mode because we won't
 | 
			
		||||
      // have an available working copy.
 | 
			
		||||
      return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    $external_classes = array();
 | 
			
		||||
    foreach ($uses as $symbol => $line) {
 | 
			
		||||
      $parts = explode('.', $symbol);
 | 
			
		||||
      $class = implode('.', array_slice($parts, 0, 2));
 | 
			
		||||
      if (!array_key_exists($class, $external_classes) &&
 | 
			
		||||
          !array_key_exists($class, $installs)) {
 | 
			
		||||
        $external_classes[$class] = $line;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    $celerity = CelerityResourceMap::getInstance();
 | 
			
		||||
 | 
			
		||||
    $info = $celerity->lookupFileInformation(substr($path, strlen('webroot')));
 | 
			
		||||
 | 
			
		||||
    $need = $external_classes;
 | 
			
		||||
 | 
			
		||||
    $requires = $info['requires'];
 | 
			
		||||
 | 
			
		||||
    foreach ($requires as $key => $name) {
 | 
			
		||||
      $symbol_info = $celerity->lookupSymbolInformation($name);
 | 
			
		||||
      if (!$symbol_info) {
 | 
			
		||||
        $this->raiseLintAtLine(
 | 
			
		||||
          0,
 | 
			
		||||
          0,
 | 
			
		||||
          self::LINT_UNKNOWN_DEPENDENCY,
 | 
			
		||||
          "This file @requires component '{$name}', but it does not ".
 | 
			
		||||
          "exist. You may need to rebuild the Celerity map.");
 | 
			
		||||
        unset($requires[$key]);
 | 
			
		||||
        continue;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      $symbol_path = 'webroot'.$symbol_info['disk'];
 | 
			
		||||
      list($ignored, $req_install) = $this->getUsedAndInstalledSymbolsForPath(
 | 
			
		||||
        $symbol_path);
 | 
			
		||||
      if (array_intersect_key($req_install, $external_classes)) {
 | 
			
		||||
        $need = array_diff_key($need, $req_install);
 | 
			
		||||
        unset($requires[$key]);
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    foreach ($need as $class => $line) {
 | 
			
		||||
      $this->raiseLintAtLine(
 | 
			
		||||
        $line,
 | 
			
		||||
        0,
 | 
			
		||||
        self::LINT_MISSING_DEPENDENCY,
 | 
			
		||||
        "This file uses '{$class}' but does not @requires the component ".
 | 
			
		||||
        "which installs it. You may need to rebuild the Celerity map.");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    foreach ($requires as $component) {
 | 
			
		||||
      $this->raiseLintAtLine(
 | 
			
		||||
        $line,
 | 
			
		||||
        0,
 | 
			
		||||
        self::LINT_UNNECESSARY_DEPENDENCY,
 | 
			
		||||
        "This file @requires component '{$component}' but does not use ".
 | 
			
		||||
        "anything it provides.");
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private function loadSymbols($path) {
 | 
			
		||||
    if (empty($this->symbols[$path])) {
 | 
			
		||||
      $this->symbols[$path] = $this->newSymbolsFuture($path)->resolvex();
 | 
			
		||||
    }
 | 
			
		||||
    return $this->symbols[$path];
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private function newSymbolsFuture($path) {
 | 
			
		||||
    $root = dirname(phutil_get_library_root('phabricator'));
 | 
			
		||||
 | 
			
		||||
    $support = $root.'/externals/javelin/support';
 | 
			
		||||
    $javelinsymbols = $support.'/javelinsymbols/javelinsymbols';
 | 
			
		||||
 | 
			
		||||
    $future = new ExecFuture($javelinsymbols.' # '.escapeshellarg($path));
 | 
			
		||||
    $future->write($this->getData($path));
 | 
			
		||||
    return $future;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private function getUsedAndInstalledSymbolsForPath($path) {
 | 
			
		||||
    list($symbols) = $this->loadSymbols($path);
 | 
			
		||||
 | 
			
		||||
    $symbols = explode("\n", trim($symbols));
 | 
			
		||||
 | 
			
		||||
    $uses = array();
 | 
			
		||||
    $installs = array();
 | 
			
		||||
    foreach ($symbols as $line) {
 | 
			
		||||
      $matches = null;
 | 
			
		||||
      if (!preg_match('/^([?+])([^:]*):(\d+)$/', $line, $matches)) {
 | 
			
		||||
        throw new Exception(
 | 
			
		||||
          "Received malformed output from `javelinsymbols`.");
 | 
			
		||||
      }
 | 
			
		||||
      $type = $matches[1];
 | 
			
		||||
      $symbol = $matches[2];
 | 
			
		||||
      $line = $matches[3];
 | 
			
		||||
 | 
			
		||||
      switch ($type) {
 | 
			
		||||
        case '?':
 | 
			
		||||
          $uses[$symbol] = $line;
 | 
			
		||||
          break;
 | 
			
		||||
        case '+':
 | 
			
		||||
          $installs['JX.'.$symbol] = $line;
 | 
			
		||||
          break;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    $contents = $this->getData($path);
 | 
			
		||||
 | 
			
		||||
    $matches = null;
 | 
			
		||||
    $count = preg_match_all(
 | 
			
		||||
      '/@javelin-installs\W+(\S+)/',
 | 
			
		||||
      $contents,
 | 
			
		||||
      $matches,
 | 
			
		||||
      PREG_PATTERN_ORDER);
 | 
			
		||||
 | 
			
		||||
    if ($count) {
 | 
			
		||||
      foreach ($matches[1] as $symbol) {
 | 
			
		||||
        $installs[$symbol] = 0;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return array($uses, $installs);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										18
									
								
								src/infrastructure/lint/linter/javelin/__init__.php
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										18
									
								
								src/infrastructure/lint/linter/javelin/__init__.php
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,18 @@
 | 
			
		||||
<?php
 | 
			
		||||
/**
 | 
			
		||||
 * This file is automatically generated. Lint this module to rebuild it.
 | 
			
		||||
 * @generated
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
phutil_require_module('arcanist', 'lint/linter/base');
 | 
			
		||||
 | 
			
		||||
phutil_require_module('phabricator', 'infrastructure/celerity/map');
 | 
			
		||||
 | 
			
		||||
phutil_require_module('phutil', 'future');
 | 
			
		||||
phutil_require_module('phutil', 'future/exec');
 | 
			
		||||
phutil_require_module('phutil', 'moduleutils');
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
phutil_require_source('PhabricatorJavelinLinter.php');
 | 
			
		||||
@@ -63,7 +63,7 @@ class AphrontTokenizerTemplateView extends AphrontView {
 | 
			
		||||
        'mustcapture' => true,
 | 
			
		||||
        'name'        => $name,
 | 
			
		||||
        'class'       => 'jx-tokenizer-input',
 | 
			
		||||
        'sigil'       => 'tokenizer',
 | 
			
		||||
        'sigil'       => 'tokenizer-input',
 | 
			
		||||
        'style'       => 'width: 0px;',
 | 
			
		||||
        'disabled'    => 'disabled',
 | 
			
		||||
        'type'        => 'text',
 | 
			
		||||
 
 | 
			
		||||
@@ -42,23 +42,9 @@ class AphrontFormTokenizerControl extends AphrontFormControl {
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  protected function renderInput() {
 | 
			
		||||
    require_celerity_resource('javelin-typeahead-dev');
 | 
			
		||||
 | 
			
		||||
    $name = $this->getName();
 | 
			
		||||
    $values = nonempty($this->getValue(), array());
 | 
			
		||||
 | 
			
		||||
    $input = javelin_render_tag(
 | 
			
		||||
      'input',
 | 
			
		||||
      array(
 | 
			
		||||
        'mustcapture' => true,
 | 
			
		||||
        'name'        => $name,
 | 
			
		||||
        'class'       => 'jx-tokenizer-input',
 | 
			
		||||
        'sigil'       => 'tokenizer',
 | 
			
		||||
        'style'       => 'width: 0px;',
 | 
			
		||||
        'disabled'    => 'disabled',
 | 
			
		||||
        'type'        => 'text',
 | 
			
		||||
      ));
 | 
			
		||||
 | 
			
		||||
    if ($this->getID()) {
 | 
			
		||||
      $id = $this->getID();
 | 
			
		||||
    } else {
 | 
			
		||||
 
 | 
			
		||||
@@ -8,7 +8,6 @@
 | 
			
		||||
 | 
			
		||||
phutil_require_module('phabricator', 'infrastructure/celerity/api');
 | 
			
		||||
phutil_require_module('phabricator', 'infrastructure/javelin/api');
 | 
			
		||||
phutil_require_module('phabricator', 'infrastructure/javelin/markup');
 | 
			
		||||
phutil_require_module('phabricator', 'view/control/tokenizer');
 | 
			
		||||
phutil_require_module('phabricator', 'view/form/control/base');
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -89,9 +89,6 @@ class PhabricatorStandardPageView extends AphrontPageView {
 | 
			
		||||
    require_celerity_resource('phabricator-core-buttons-css');
 | 
			
		||||
    require_celerity_resource('phabricator-standard-page-view');
 | 
			
		||||
 | 
			
		||||
    require_celerity_resource('javelin-lib-dev');
 | 
			
		||||
    require_celerity_resource('javelin-workflow-dev');
 | 
			
		||||
 | 
			
		||||
    Javelin::initBehavior('workflow', array());
 | 
			
		||||
 | 
			
		||||
    if ($console) {
 | 
			
		||||
@@ -118,8 +115,7 @@ class PhabricatorStandardPageView extends AphrontPageView {
 | 
			
		||||
        'window.__DEV__=1;'.
 | 
			
		||||
      '</script>'.
 | 
			
		||||
      $response->renderResourcesOfType('css').
 | 
			
		||||
      '<script type="text/javascript" src="/rsrc/js/javelin/init.dev.js">'.
 | 
			
		||||
      '</script>';
 | 
			
		||||
      $response->renderSingleResource('javelin-magical-init');
 | 
			
		||||
 | 
			
		||||
    $request = $this->getRequest();
 | 
			
		||||
    if ($request) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,5 +1,8 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-install
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 * @provides multirow-row-manager
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 
 | 
			
		||||
@@ -1,5 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-dark-console
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('dark-console', function(config) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-error-log
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
var current_details = null;
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-phabricator-object-selector
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('phabricator-object-selector', function(config) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-aphront-basic-tokenizer
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-typeahead
 | 
			
		||||
 *           javelin-tokenizer
 | 
			
		||||
 *           javelin-typeahead-preloaded-source
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('aphront-basic-tokenizer', function(config) {
 | 
			
		||||
@@ -10,7 +14,7 @@ JX.behavior('aphront-basic-tokenizer', function(config) {
 | 
			
		||||
 | 
			
		||||
  var typeahead = new JX.Typeahead(
 | 
			
		||||
    root,
 | 
			
		||||
    JX.DOM.find(root, 'input', 'tokenizer'));
 | 
			
		||||
    JX.DOM.find(root, 'input', 'tokenizer-input'));
 | 
			
		||||
  typeahead.setDatasource(datasource);
 | 
			
		||||
 | 
			
		||||
  var tokenizer = new JX.Tokenizer(root);
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,8 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-workflow
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-workflow
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('workflow', function() {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-add-reviewers
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-tokenizer
 | 
			
		||||
 *           javelin-typeahead
 | 
			
		||||
 *           javelin-typeahead-preloaded-source
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-add-reviewers', function(config) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-feedback-preview
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-feedback-preview', function(config) {
 | 
			
		||||
@@ -28,7 +32,7 @@ JX.behavior('differential-feedback-preview', function(config) {
 | 
			
		||||
      cval = content.value;
 | 
			
		||||
 | 
			
		||||
      request = new JX.Request(config.uri, function(r) {
 | 
			
		||||
        preview && JX.DOM.setContent(preview, JX.HTML(r));
 | 
			
		||||
        preview && JX.DOM.setContent(preview, JX.$H(r));
 | 
			
		||||
        min = new Date().getTime() + 500;
 | 
			
		||||
        defer && defer.stop();
 | 
			
		||||
        defer = JX.defer(check, 500);
 | 
			
		||||
@@ -51,7 +55,7 @@ JX.behavior('differential-feedback-preview', function(config) {
 | 
			
		||||
 | 
			
		||||
  function refreshInlinePreview() {
 | 
			
		||||
    new JX.Request(config.inlineuri, function(r) {
 | 
			
		||||
        JX.DOM.setContent(JX.$(config.inline), JX.HTML(r));
 | 
			
		||||
        JX.DOM.setContent(JX.$(config.inline), JX.$H(r));
 | 
			
		||||
      })
 | 
			
		||||
      .setTimeout(5000)
 | 
			
		||||
      .send();
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,8 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-diff-radios
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-diff-radios', function(config) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-edit-inline-comments
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-workflow
 | 
			
		||||
 *           javelin-vector
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-edit-inline-comments', function(config) {
 | 
			
		||||
@@ -27,9 +31,9 @@ JX.behavior('differential-edit-inline-comments', function(config) {
 | 
			
		||||
    }
 | 
			
		||||
    var code = target.nextSibling;
 | 
			
		||||
 | 
			
		||||
    var pos = JX.$V(top).add(1 + JX.$V.getDim(target).x, 0);
 | 
			
		||||
    var dim = JX.$V.getDim(code).add(-4, 0);
 | 
			
		||||
    dim.y = (JX.$V(bot).y - pos.y) + JX.$V.getDim(bot).y;
 | 
			
		||||
    var pos = JX.$V(top).add(1 + JX.Vector.getDim(target).x, 0);
 | 
			
		||||
    var dim = JX.Vector.getDim(code).add(-4, 0);
 | 
			
		||||
    dim.y = (JX.$V(bot).y - pos.y) + JX.Vector.getDim(bot).y;
 | 
			
		||||
 | 
			
		||||
    pos.setPos(reticle);
 | 
			
		||||
    dim.setDim(reticle);
 | 
			
		||||
@@ -48,7 +52,7 @@ JX.behavior('differential-edit-inline-comments', function(config) {
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  function drawInlineComment(table, anchor, r) {
 | 
			
		||||
    copyRows(table, JX.$N('div', JX.HTML(r.markup)), anchor);
 | 
			
		||||
    copyRows(table, JX.$N('div', JX.$H(r.markup)), anchor);
 | 
			
		||||
    finishSelect();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
@@ -245,7 +249,7 @@ JX.behavior('differential-edit-inline-comments', function(config) {
 | 
			
		||||
      var data = {
 | 
			
		||||
        op: e.getNode('differential-inline-edit') ? 'edit' : 'delete',
 | 
			
		||||
        id: e.getNodeData('differential-inline-comment').id,
 | 
			
		||||
        on_right: e.getNodeData('differential-inline-comment').on_right,
 | 
			
		||||
        on_right: e.getNodeData('differential-inline-comment').on_right
 | 
			
		||||
      };
 | 
			
		||||
      new JX.Workflow(config.uri, data)
 | 
			
		||||
        .setHandler(function(r) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,12 +1,15 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-populate
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-populate', function(config) {
 | 
			
		||||
 | 
			
		||||
  function onresponse(target, response) {
 | 
			
		||||
    JX.DOM.replace(JX.$(target), JX.HTML(response));
 | 
			
		||||
    JX.DOM.replace(JX.$(target), JX.$H(response));
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  for (var k in config.registry) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,8 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-show-all-comments
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-show-all-comments', function(config) {
 | 
			
		||||
@@ -11,7 +13,7 @@ JX.behavior('differential-show-all-comments', function(config) {
 | 
			
		||||
    function(e) {
 | 
			
		||||
      JX.DOM.setContent(
 | 
			
		||||
        e.getNode('differential-all-comments-container'),
 | 
			
		||||
        JX.HTML(config.markup));
 | 
			
		||||
        JX.$H(config.markup));
 | 
			
		||||
      e.kill();
 | 
			
		||||
    });
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,12 +1,16 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-differential-show-more
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('differential-show-more', function(config) {
 | 
			
		||||
 | 
			
		||||
  function onresponse(origin, response) {
 | 
			
		||||
    var div = JX.$N('div', {}, JX.HTML(response));
 | 
			
		||||
    var div = JX.$N('div', {}, JX.$H(response));
 | 
			
		||||
    var anchor = origin.getNode('context-target');
 | 
			
		||||
    var root = anchor.parentNode;
 | 
			
		||||
    copyRows(root, div, anchor);
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,9 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-diffusion-jump-to
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-vector
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('diffusion-jump-to', function(config) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,9 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-diffusion-pull-lastmodified
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('diffusion-pull-lastmodified', function(config) {
 | 
			
		||||
@@ -9,7 +12,7 @@ JX.behavior('diffusion-pull-lastmodified', function(config) {
 | 
			
		||||
    new JX.Request(uri, JX.bind(config[uri], function(r) {
 | 
			
		||||
      for (var k in r) {
 | 
			
		||||
        if (this[k]) {
 | 
			
		||||
          JX.DOM.setContent(JX.$(this[k]), JX.HTML(r[k]));
 | 
			
		||||
          JX.DOM.setContent(JX.$(this[k]), JX.$H(r[k]));
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    })).send();
 | 
			
		||||
 
 | 
			
		||||
@@ -1,8 +1,13 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires multirow-row-manager
 | 
			
		||||
 *           javelin-lib-dev
 | 
			
		||||
 *           javelin-typeahead-dev
 | 
			
		||||
 *           path-typeahead
 | 
			
		||||
 *           javelin-install
 | 
			
		||||
 *           javelin-typeahead
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-tokenizer
 | 
			
		||||
 *           javelin-typeahead-preloaded-source
 | 
			
		||||
 *           javelin-stratcom
 | 
			
		||||
 *           javelin-json
 | 
			
		||||
 * @provides herald-rule-editor
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
@@ -257,7 +262,7 @@ JX.install('HeraldRuleEditor', {
 | 
			
		||||
    _newTokenizer : function(type) {
 | 
			
		||||
      var template = JX.$N(
 | 
			
		||||
        'div',
 | 
			
		||||
        new JX.HTML(this._config.template.markup));
 | 
			
		||||
        JX.$H(this._config.template.markup));
 | 
			
		||||
      template = template.firstChild;
 | 
			
		||||
      template.id = '';
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 *           javelin-typeahead-dev
 | 
			
		||||
 * @requires javelin-install
 | 
			
		||||
 *           javelin-typeahead
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-typeahead-ondemand-source
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 * @provides path-typeahead
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires herald-rule-editor
 | 
			
		||||
 *           javelin-lib-dev
 | 
			
		||||
 *           javelin-behavior
 | 
			
		||||
 * @provides javelin-behavior-herald-rule-editor
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,10 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @provides javelin-behavior-maniphest-transaction-controls
 | 
			
		||||
 * @requires javelin-lib-dev
 | 
			
		||||
 * @requires javelin-behavior
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-tokenizer
 | 
			
		||||
 *           javelin-typeahead
 | 
			
		||||
 *           javelin-typeahead-preloaded-source
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.behavior('maniphest-transaction-controls', function(config) {
 | 
			
		||||
@@ -51,31 +55,5 @@ JX.behavior('maniphest-transaction-controls', function(config) {
 | 
			
		||||
      }
 | 
			
		||||
    });
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 | 
			
		||||
  var root = JX.$(config.tokenizer);
 | 
			
		||||
  var datasource = new JX.TypeaheadPreloadedSource(config.src);
 | 
			
		||||
 | 
			
		||||
  var typeahead = new JX.Typeahead(root);
 | 
			
		||||
  typeahead.setDatasource(datasource);
 | 
			
		||||
 | 
			
		||||
  var tokenizer = new JX.Tokenizer(root);
 | 
			
		||||
  tokenizer.setTypeahead(typeahead);
 | 
			
		||||
  tokenizer.start();
 | 
			
		||||
 | 
			
		||||
  JX.DOM.listen(
 | 
			
		||||
    JX.$(config.select),
 | 
			
		||||
    'change',
 | 
			
		||||
    null,
 | 
			
		||||
    function(e) {
 | 
			
		||||
      if (JX.$(config.select).value == 'add_reviewers') {
 | 
			
		||||
        JX.DOM.show(JX.$(config.row));
 | 
			
		||||
        tokenizer.refresh();
 | 
			
		||||
      } else {
 | 
			
		||||
        JX.DOM.hide(JX.$(config.row));
 | 
			
		||||
      }
 | 
			
		||||
    });
 | 
			
		||||
 | 
			
		||||
*/
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,8 +1,9 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires multirow-row-manager
 | 
			
		||||
 *           javelin-lib-dev
 | 
			
		||||
 *           javelin-typeahead-dev
 | 
			
		||||
 *           javelin-install
 | 
			
		||||
 *           path-typeahead
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 * @provides owners-path-editor
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
@@ -105,7 +106,7 @@ JX.install('OwnersPathEditor', {
 | 
			
		||||
      var repo_cell = JX.$N('td', {}, repo_select);
 | 
			
		||||
      var typeahead_cell = JX.$N(
 | 
			
		||||
        'td',
 | 
			
		||||
        JX.HTML(this._inputTemplate));
 | 
			
		||||
        JX.$H(this._inputTemplate));
 | 
			
		||||
 | 
			
		||||
      // Text input for path.
 | 
			
		||||
      var path_input = JX.DOM.find(typeahead_cell, 'input');
 | 
			
		||||
@@ -113,7 +114,7 @@ JX.install('OwnersPathEditor', {
 | 
			
		||||
        path_input,
 | 
			
		||||
        {
 | 
			
		||||
          value : path_ref.path || "",
 | 
			
		||||
          name : "path[" + this._count + "]",
 | 
			
		||||
          name : "path[" + this._count + "]"
 | 
			
		||||
        });
 | 
			
		||||
 | 
			
		||||
      // The Typeahead requires a display div called hardpoint.
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @requires owners-path-editor
 | 
			
		||||
 *           javelin-lib-dev
 | 
			
		||||
 *           javelin-behavior
 | 
			
		||||
 * @provides javelin-behavior-owners-path-editor
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										1
									
								
								webroot/rsrc/js/javelin
									
									
									
									
									
										Symbolic link
									
								
							
							
						
						
									
										1
									
								
								webroot/rsrc/js/javelin
									
									
									
									
									
										Symbolic link
									
								
							@@ -0,0 +1 @@
 | 
			
		||||
../../../externals/javelin/src/
 | 
			
		||||
@@ -1,179 +0,0 @@
 | 
			
		||||
/**
 | 
			
		||||
 * Javelin core; installs Javelin and Stratcom event delegation.
 | 
			
		||||
 *
 | 
			
		||||
 * @provides javelin-magical-init
 | 
			
		||||
 * @nopackage
 | 
			
		||||
 *
 | 
			
		||||
 * @javelin-installs JX.__rawEventQueue
 | 
			
		||||
 * @javelin-installs JX.__simulate
 | 
			
		||||
 * @javelin-installs JX.enableDispatch
 | 
			
		||||
 * @javelin-installs JX.onload
 | 
			
		||||
 *
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
(function() {
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
  if (window.JX) {
 | 
			
		||||
    return;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  window.JX = {};
 | 
			
		||||
  window['__DEV__'] = window['__DEV__'] || 0;
 | 
			
		||||
 | 
			
		||||
  var loaded = false;
 | 
			
		||||
  var onload = [];
 | 
			
		||||
  var master_event_queue = [];
 | 
			
		||||
  var root = document.documentElement;
 | 
			
		||||
  var has_add_event_listener = !!root.addEventListener;
 | 
			
		||||
 | 
			
		||||
  JX.__rawEventQueue = function(what) {
 | 
			
		||||
    master_event_queue.push(what);
 | 
			
		||||
 | 
			
		||||
    // Evade static analysis - JX.Stratcom
 | 
			
		||||
    var Stratcom = JX['Stratcom'];
 | 
			
		||||
    if (Stratcom && Stratcom.ready) {
 | 
			
		||||
      //  Empty the queue now so that exceptions don't cause us to repeatedly
 | 
			
		||||
      //  try to handle events.
 | 
			
		||||
      var local_queue = master_event_queue;
 | 
			
		||||
      master_event_queue = [];
 | 
			
		||||
      for (var ii = 0; ii < local_queue.length; ++ii) {
 | 
			
		||||
        var evt = local_queue[ii];
 | 
			
		||||
 | 
			
		||||
        //  Sometimes IE gives us events which throw when ".type" is accessed;
 | 
			
		||||
        //  just ignore them since we can't meaningfully dispatch them. TODO:
 | 
			
		||||
        //  figure out where these are coming from.
 | 
			
		||||
        try { var test = evt.type; } catch (x) { continue; }
 | 
			
		||||
 | 
			
		||||
        if (!loaded && evt.type == 'domready') {
 | 
			
		||||
          document.body && (document.body.id = null);
 | 
			
		||||
          loaded = true;
 | 
			
		||||
 | 
			
		||||
          for (var ii = 0; ii < onload.length; ii++) {
 | 
			
		||||
            onload[ii]();
 | 
			
		||||
          }
 | 
			
		||||
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Stratcom.dispatch(evt);
 | 
			
		||||
      }
 | 
			
		||||
    } else {
 | 
			
		||||
      var target = what.srcElement || what.target;
 | 
			
		||||
      if (target &&
 | 
			
		||||
          (what.type in {click: 1, submit: 1}) &&
 | 
			
		||||
          target.getAttribute &&
 | 
			
		||||
          target.getAttribute('data-mustcapture') === '1') {
 | 
			
		||||
        what.returnValue = false;
 | 
			
		||||
        what.preventDefault && what.preventDefault();
 | 
			
		||||
        document.body.id = 'event_capture';
 | 
			
		||||
 | 
			
		||||
        // For versions of IE that use attachEvent, the event object is somehow
 | 
			
		||||
        // stored globally by reference, and all the references we push to the
 | 
			
		||||
        // master_event_queue will always refer to the most recent event. We
 | 
			
		||||
        // work around this by popping the useless global event off the queue,
 | 
			
		||||
        // and pushing a clone of the event that was just fired using the IE's
 | 
			
		||||
        // proprietary createEventObject function.
 | 
			
		||||
        // see: http://msdn.microsoft.com/en-us/library/ms536390(v=vs.85).aspx
 | 
			
		||||
        if (!add_event_listener && document.createEventObject) {
 | 
			
		||||
          master_event_queue.pop();
 | 
			
		||||
          master_event_queue.push(document.createEventObject(what));
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return false;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  JX.enableDispatch = function(target, type) {
 | 
			
		||||
    if (target.addEventListener) {
 | 
			
		||||
      target.addEventListener(type, JX.__rawEventQueue, true);
 | 
			
		||||
    } else if (target.attachEvent) {
 | 
			
		||||
      target.attachEvent('on' + type, JX.__rawEventQueue);
 | 
			
		||||
    }
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  var document_events = [
 | 
			
		||||
    'click',
 | 
			
		||||
    'change',
 | 
			
		||||
    'keypress',
 | 
			
		||||
    'mousedown',
 | 
			
		||||
    'mouseover',
 | 
			
		||||
    'mouseout',
 | 
			
		||||
    'mouseup',
 | 
			
		||||
    'keydown',
 | 
			
		||||
    'drop',
 | 
			
		||||
    'dragenter',
 | 
			
		||||
    'dragleave',
 | 
			
		||||
    'dragover'
 | 
			
		||||
  ];
 | 
			
		||||
 | 
			
		||||
  //  Simulate focus and blur in old versions of IE using focusin and focusout
 | 
			
		||||
  //  TODO: Document the gigantic IE mess here with focus/blur.
 | 
			
		||||
  //  TODO: beforeactivate/beforedeactivate?
 | 
			
		||||
  //  http://www.quirksmode.org/blog/archives/2008/04/delegating_the.html
 | 
			
		||||
  if (!has_add_event_listener) {
 | 
			
		||||
    document_events.push('focusin', 'focusout');
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  //  Opera is multilol: it propagates focus / blur odd, and submit differently
 | 
			
		||||
  if (window.opera) {
 | 
			
		||||
    document_events.push('focus', 'blur');
 | 
			
		||||
  } else {
 | 
			
		||||
    document_events.push('submit');
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  for (var ii = 0; ii < document_events.length; ++ii) {
 | 
			
		||||
    JX.enableDispatch(root, document_events[ii]);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  //  In particular, we're interested in capturing window focus/blur here so
 | 
			
		||||
  //  long polls can abort when the window is not focused.
 | 
			
		||||
  var window_events = [
 | 
			
		||||
    ('onpagehide' in window) ? 'pagehide' : 'unload',
 | 
			
		||||
    'resize',
 | 
			
		||||
    'focus',
 | 
			
		||||
    'blur'
 | 
			
		||||
  ];
 | 
			
		||||
 | 
			
		||||
  for (var ii = 0; ii < window_events.length; ++ii) {
 | 
			
		||||
    JX.enableDispatch(window, window_events[ii]);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  JX.__simulate = function(node, event) {
 | 
			
		||||
    if (!has_add_event_listener) {
 | 
			
		||||
      var e = {target: node, type: event};
 | 
			
		||||
      JX.__rawEventQueue(e);
 | 
			
		||||
      if (e.returnValue === false) {
 | 
			
		||||
        return false;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  if (has_add_event_listener) {
 | 
			
		||||
    document.addEventListener('DOMContentLoaded', function() {
 | 
			
		||||
      JX.__rawEventQueue({type: 'domready'});
 | 
			
		||||
    }, true);
 | 
			
		||||
  } else {
 | 
			
		||||
    var ready =
 | 
			
		||||
      "if (this.readyState == 'complete') {" +
 | 
			
		||||
        "JX.__rawEventQueue({type: 'domready'});" +
 | 
			
		||||
      "}";
 | 
			
		||||
 | 
			
		||||
    document.write(
 | 
			
		||||
      '<script' +
 | 
			
		||||
      ' defer="defer"' +
 | 
			
		||||
      ' src="javascript:void(0)"' +
 | 
			
		||||
      ' onreadystatechange="' + ready + '"' +
 | 
			
		||||
      '><\/sc' + 'ript\>');
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  JX.onload = function(func) {
 | 
			
		||||
    if (loaded) {
 | 
			
		||||
      func();
 | 
			
		||||
    } else {
 | 
			
		||||
      onload.push(func);
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
})();
 | 
			
		||||
							
								
								
									
										2
									
								
								webroot/rsrc/js/javelin/init.min.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								webroot/rsrc/js/javelin/init.min.js
									
									
									
									
										vendored
									
									
								
							@@ -1,2 +0,0 @@
 | 
			
		||||
/** @provides javelin-init-prod */
 | 
			
		||||
(function(){if(window.JX)return;window.JX={};window.__DEV__=window.__DEV__||0;var d=false;var f=[];var e=[];var h=document.documentElement;var b=!!h.addEventListener;JX.__rawEventQueue=function(o){e.push(o);var j=JX.Stratcom;if(j&&j.ready){var m=e;e=[];for(var l=0;l<m.length;++l){var k=m[l];try{var test=k.type;}catch(p){continue;}if(!d&&k.type=='domready'){document.body&&(document.body.id=null);d=true;for(var l=0;l<f.length;l++)f[l]();}j.dispatch(k);}}else{var n=o.srcElement||o.target;if(n&&(o.type in {click:1,submit:1})&&n.getAttribute&&n.getAttribute('data-mustcapture')==='1'){o.returnValue=false;o.preventDefault&&o.preventDefault();document.body.id='event_capture';if(!add_event_listener&&document.createEventObject){e.pop();e.push(document.createEventObject(o));}return false;}}};JX.enableDispatch=function(j,k){if(j.addEventListener){j.addEventListener(k,JX.__rawEventQueue,true);}else if(j.attachEvent)j.attachEvent('on'+k,JX.__rawEventQueue);};var a=['click','change','keypress','mousedown','mouseover','mouseout','mouseup','keydown','drop','dragenter','dragleave','dragover'];if(!b)a.push('focusin','focusout');if(window.opera){a.push('focus','blur');}else a.push('submit');for(var c=0;c<a.length;++c)JX.enableDispatch(h,a[c]);var i=[('onpagehide' in window)?'pagehide':'unload','resize','focus','blur'];for(var c=0;c<i.length;++c)JX.enableDispatch(window,i[c]);JX.__simulate=function(k,event){if(!b){var j={target:k,type:event};JX.__rawEventQueue(j);if(j.returnValue===false)return false;}};if(b){document.addEventListener('DOMContentLoaded',function(){JX.__rawEventQueue({type:'domready'});},true);}else{var g="if (this.readyState == 'complete') {"+"JX.__rawEventQueue({type: 'domready'});"+"}";document.write('<script'+' defer="defer"'+' src="javascript:void(0)"'+' onreadystatechange="'+g+'"'+'><\/sc'+'ript\>');}JX.onload=function(j){if(d){j();}else f.push(j);};})();
 | 
			
		||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										3
									
								
								webroot/rsrc/js/javelin/javelin.min.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										3
									
								
								webroot/rsrc/js/javelin/javelin.min.js
									
									
									
									
										vendored
									
									
								
							
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							
							
								
								
									
										3
									
								
								webroot/rsrc/js/javelin/typeahead.min.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										3
									
								
								webroot/rsrc/js/javelin/typeahead.min.js
									
									
									
									
										vendored
									
									
								
							
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							@@ -1,242 +0,0 @@
 | 
			
		||||
/** @provides javelin-workflow-dev */
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * @requires javelin-install javelin-vector javelin-dom
 | 
			
		||||
 * @provides javelin-mask
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Show a transparent "mask" over the page; used by Workflow to draw visual
 | 
			
		||||
 * attention to modal dialogs.
 | 
			
		||||
 */
 | 
			
		||||
JX.install('Mask', {
 | 
			
		||||
  statics : {
 | 
			
		||||
    _depth : 0,
 | 
			
		||||
    _mask : null,
 | 
			
		||||
    show : function() {
 | 
			
		||||
      if (!JX.Mask._depth) {
 | 
			
		||||
        JX.Mask._mask = JX.$N('div', {className: 'jx-mask'});
 | 
			
		||||
        document.body.appendChild(JX.Mask._mask);
 | 
			
		||||
        JX.$V.getDocument().setDim(JX.Mask._mask);
 | 
			
		||||
      }
 | 
			
		||||
      ++JX.Mask._depth;
 | 
			
		||||
    },
 | 
			
		||||
    hide : function() {
 | 
			
		||||
      --JX.Mask._depth;
 | 
			
		||||
      if (!JX.Mask._depth) {
 | 
			
		||||
        JX.DOM.remove(JX.Mask._mask);
 | 
			
		||||
        JX.Mask._mask = null;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
});
 | 
			
		||||
/**
 | 
			
		||||
 * @requires javelin-stratcom
 | 
			
		||||
 *           javelin-request
 | 
			
		||||
 *           javelin-dom
 | 
			
		||||
 *           javelin-vector
 | 
			
		||||
 *           javelin-install
 | 
			
		||||
 *           javelin-util
 | 
			
		||||
 *           javelin-mask
 | 
			
		||||
 * @provides javelin-workflow
 | 
			
		||||
 * @javelin
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
JX.install('Workflow', {
 | 
			
		||||
  construct : function(uri, data) {
 | 
			
		||||
    if (__DEV__) {
 | 
			
		||||
      if (!uri || uri == '#') {
 | 
			
		||||
        throw new Error(
 | 
			
		||||
          'new JX.Workflow(<?>, ...): '+
 | 
			
		||||
          'bogus URI provided when creating workflow.');
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
    this.setURI(uri);
 | 
			
		||||
    this.setData(data || {});
 | 
			
		||||
  },
 | 
			
		||||
 | 
			
		||||
  events : ['error', 'finally', 'submit'],
 | 
			
		||||
 | 
			
		||||
  statics : {
 | 
			
		||||
    _stack   : [],
 | 
			
		||||
    newFromForm : function(form, data) {
 | 
			
		||||
      var inputs = [].concat(
 | 
			
		||||
        JX.DOM.scry(form, 'input'),
 | 
			
		||||
        JX.DOM.scry(form, 'button'),
 | 
			
		||||
        JX.DOM.scry(form, 'textarea'));
 | 
			
		||||
 | 
			
		||||
      for (var ii = 0; ii < inputs.length; ii++) {
 | 
			
		||||
        if (inputs[ii].disabled) {
 | 
			
		||||
          delete inputs[ii];
 | 
			
		||||
        } else {
 | 
			
		||||
          inputs[ii].disabled = true;
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      var workflow = new JX.Workflow(
 | 
			
		||||
        form.getAttribute('action'),
 | 
			
		||||
        JX.copy(data || {}, JX.DOM.serialize(form)));
 | 
			
		||||
      workflow.setMethod(form.getAttribute('method'));
 | 
			
		||||
      workflow.listen('finally', function() {
 | 
			
		||||
        for (var ii = 0; ii < inputs.length; ii++) {
 | 
			
		||||
          inputs[ii] && (inputs[ii].disabled = false);
 | 
			
		||||
        }
 | 
			
		||||
      });
 | 
			
		||||
      return workflow;
 | 
			
		||||
    },
 | 
			
		||||
    newFromLink : function(link) {
 | 
			
		||||
      var workflow = new JX.Workflow(link.href);
 | 
			
		||||
      return workflow;
 | 
			
		||||
    },
 | 
			
		||||
    _push : function(workflow) {
 | 
			
		||||
      JX.Mask.show();
 | 
			
		||||
      JX.Workflow._stack.push(workflow);
 | 
			
		||||
    },
 | 
			
		||||
    _pop : function() {
 | 
			
		||||
      var dialog = JX.Workflow._stack.pop();
 | 
			
		||||
      (dialog.getCloseHandler() || JX.bag)();
 | 
			
		||||
      dialog._destroy();
 | 
			
		||||
      JX.Mask.hide();
 | 
			
		||||
    },
 | 
			
		||||
    disable : function() {
 | 
			
		||||
      JX.Workflow._disabled = true;
 | 
			
		||||
    },
 | 
			
		||||
    _onbutton : function(event) {
 | 
			
		||||
 | 
			
		||||
      if (JX.Stratcom.pass()) {
 | 
			
		||||
        return;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      if (JX.Workflow._disabled) {
 | 
			
		||||
        return;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      var t = event.getTarget();
 | 
			
		||||
      if (t.name == '__cancel__' || t.name == '__close__') {
 | 
			
		||||
        JX.Workflow._pop();
 | 
			
		||||
      } else {
 | 
			
		||||
 | 
			
		||||
        var form = event.getNode('jx-dialog');
 | 
			
		||||
        var data = JX.DOM.serialize(form);
 | 
			
		||||
        data[t.name] = true;
 | 
			
		||||
        data.__wflow__ = true;
 | 
			
		||||
 | 
			
		||||
        var active = JX.Workflow._stack[JX.Workflow._stack.length - 1];
 | 
			
		||||
        var e = active.invoke('submit', {form: form, data: data});
 | 
			
		||||
        if (!e.getStopped()) {
 | 
			
		||||
          active._destroy();
 | 
			
		||||
          active
 | 
			
		||||
            .setURI(form.getAttribute('action') || active.getURI())
 | 
			
		||||
            .setData(data)
 | 
			
		||||
            .start();
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
      event.prevent();
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
 | 
			
		||||
  members : {
 | 
			
		||||
    _root : null,
 | 
			
		||||
    _pushed : false,
 | 
			
		||||
    _onload : function(r) {
 | 
			
		||||
      // It is permissible to send back a falsey redirect to force a page
 | 
			
		||||
      // reload, so we need to take this branch if the key is present.
 | 
			
		||||
      if (r && (typeof r.redirect != 'undefined')) {
 | 
			
		||||
        JX.go(r.redirect, true);
 | 
			
		||||
      } else if (r && r.dialog) {
 | 
			
		||||
        this._push();
 | 
			
		||||
        this._root = JX.$N(
 | 
			
		||||
          'div',
 | 
			
		||||
          {className: 'jx-client-dialog'},
 | 
			
		||||
          JX.HTML(r.dialog));
 | 
			
		||||
        JX.DOM.listen(
 | 
			
		||||
          this._root,
 | 
			
		||||
          'click',
 | 
			
		||||
          [['jx-workflow-button'], ['tag:button']],
 | 
			
		||||
          JX.Workflow._onbutton);
 | 
			
		||||
        document.body.appendChild(this._root);
 | 
			
		||||
        var d = JX.$V.getDim(this._root);
 | 
			
		||||
        var v = JX.$V.getViewport();
 | 
			
		||||
        var s = JX.$V.getScroll();
 | 
			
		||||
        JX.$V((v.x - d.x) / 2, s.y + 100).setPos(this._root);
 | 
			
		||||
        try {
 | 
			
		||||
          try {
 | 
			
		||||
            JX.DOM.focus(JX.DOM.find(this._root, 'button', '__default__'));
 | 
			
		||||
          } catch (_ignored) {}
 | 
			
		||||
          var inputs = JX.DOM.scry(this._root, 'input')
 | 
			
		||||
                         .concat(JX.DOM.scry(this._root, 'textarea'));
 | 
			
		||||
          var miny = Number.POSITIVE_INFINITY;
 | 
			
		||||
          var target = null;
 | 
			
		||||
          for (var ii = 0; ii < inputs.length; ++ii) {
 | 
			
		||||
            if (inputs[ii].type != 'hidden') {
 | 
			
		||||
              // Find the topleft-most displayed element.
 | 
			
		||||
              var p = JX.$V(inputs[ii]);
 | 
			
		||||
              if (p.y < miny) {
 | 
			
		||||
                 miny = p.y;
 | 
			
		||||
                 target = inputs[ii];
 | 
			
		||||
              }
 | 
			
		||||
            }
 | 
			
		||||
          }
 | 
			
		||||
          target && JX.DOM.focus(target);
 | 
			
		||||
        } catch (_ignored) {}
 | 
			
		||||
      } else if (this.getHandler()) {
 | 
			
		||||
        this.getHandler()(r);
 | 
			
		||||
        this._pop();
 | 
			
		||||
      } else if (r) {
 | 
			
		||||
        if (__DEV__) {
 | 
			
		||||
          throw new Error('Response to workflow request went unhandled.');
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    _push : function() {
 | 
			
		||||
      if (!this._pushed) {
 | 
			
		||||
        this._pushed = true;
 | 
			
		||||
        JX.Workflow._push(this);
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    _pop : function() {
 | 
			
		||||
      if (this._pushed) {
 | 
			
		||||
        this._pushed = false;
 | 
			
		||||
        JX.Workflow._pop();
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    _destroy : function() {
 | 
			
		||||
      if (this._root) {
 | 
			
		||||
        JX.DOM.remove(this._root);
 | 
			
		||||
        this._root = null;
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    start : function() {
 | 
			
		||||
      var uri = this.getURI();
 | 
			
		||||
      var method = this.getMethod();
 | 
			
		||||
      var r = new JX.Request(uri, JX.bind(this, this._onload));
 | 
			
		||||
      r.setData(this.getData());
 | 
			
		||||
      r.setDataSerializer(this.getDataSerializer());
 | 
			
		||||
      if (method) {
 | 
			
		||||
        r.setMethod(method);
 | 
			
		||||
      }
 | 
			
		||||
      r.listen('finally', JX.bind(this, this.invoke, 'finally'));
 | 
			
		||||
      r.listen('error', JX.bind(this, function(error) {
 | 
			
		||||
        var e = this.invoke('error', error);
 | 
			
		||||
        if (e.getStopped()) {
 | 
			
		||||
          return;
 | 
			
		||||
        }
 | 
			
		||||
        // TODO: Default error behavior? On Facebook Lite, we just shipped the
 | 
			
		||||
        // user to "/error/". We could emit a blanket 'workflow-failed' type
 | 
			
		||||
        // event instead.
 | 
			
		||||
      }));
 | 
			
		||||
      r.send();
 | 
			
		||||
    }
 | 
			
		||||
  },
 | 
			
		||||
 | 
			
		||||
  properties : {
 | 
			
		||||
    handler : null,
 | 
			
		||||
    closeHandler : null,
 | 
			
		||||
    data : null,
 | 
			
		||||
    dataSerializer : null,
 | 
			
		||||
    method : null,
 | 
			
		||||
    URI : null
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
});
 | 
			
		||||
							
								
								
									
										3
									
								
								webroot/rsrc/js/javelin/workflow.min.js
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										3
									
								
								webroot/rsrc/js/javelin/workflow.min.js
									
									
									
									
										vendored
									
									
								
							@@ -1,3 +0,0 @@
 | 
			
		||||
/** @provides javelin-workflow-prod */
 | 
			
		||||
 | 
			
		||||
JX.install('Mask',{statics:{_a:0,_b:null,show:function(){if(!JX.Mask._a){JX.Mask._b=JX.$N('div',{className:'jx-mask'});document.body.appendChild(JX.Mask._b);JX.$V.getDocument().setDim(JX.Mask._b);}++JX.Mask._a;},hide:function(){--JX.Mask._a;if(!JX.Mask._a){JX.DOM.remove(JX.Mask._b);JX.Mask._b=null;}}}});JX.install('Workflow',{construct:function(b,a){this.setURI(b);this.setData(a||{});},events:['error','finally','submit'],statics:{_c:[],newFromForm:function(b,a){var d=[].concat(JX.DOM.scry(b,'input'),JX.DOM.scry(b,'button'),JX.DOM.scry(b,'textarea'));for(var c=0;c<d.length;c++)if(d[c].disabled){delete d[c];}else d[c].disabled=true;var e=new JX.Workflow(b.getAttribute('action'),JX.copy(a||{},JX.DOM.serialize(b)));e.setMethod(b.getAttribute('method'));e.listen('finally',function(){for(var f=0;f<d.length;f++)d[f]&&(d[f].disabled=false);});return e;},newFromLink:function(a){var b=new JX.Workflow(a.href);return b;},_d:function(a){JX.Mask.show();JX.Workflow._c.push(a);},_e:function(){var a=JX.Workflow._c.pop();(a.getCloseHandler()||JX.bag)();a._f();JX.Mask.hide();},disable:function(){JX.Workflow._g=true;},_h:function(event){if(JX.Stratcom.pass())return;if(JX.Workflow._g)return;var e=event.getTarget();if(e.name=='__cancel__'||e.name=='__close__'){JX.Workflow._e();}else{var d=event.getNode('jx-dialog');var b=JX.DOM.serialize(d);b[e.name]=true;b.__wflow__=true;var a=JX.Workflow._c[JX.Workflow._c.length-1];var c=a.invoke('submit',{form:d,data:b});if(!c.getStopped()){a._f();a.setURI(d.getAttribute('action')||a.getURI()).setData(b).start();}}event.prevent();}},members:{_i:null,_j:false,_k:function(c){if(c&&(typeof c.redirect!='undefined')){JX.go(c.redirect,true);}else if(c&&c.dialog){this._d();this._i=JX.$N('div',{className:'jx-client-dialog'},JX.HTML(c.dialog));JX.DOM.listen(this._i,'click','tag:button',JX.Workflow._h);document.body.appendChild(this._i);var b=JX.$V.getDim(this._i);var e=JX.$V.getViewport();var d=JX.$V.getScroll();JX.$V((e.x-b.x)/2,d.y+100).setPos(this._i);try{JX.DOM.focus(JX.DOM.find(this._i,'button','__default__'));var inputs=JX.DOM.scry(this._i,'input').concat(JX.DOM.scry(this._i,'textarea'));var miny=Number.POSITIVE_INFINITY;var target=null;for(var ii=0;ii<inputs.length;++ii)if(inputs[ii].type!='hidden'){var p=JX.$V(inputs[ii]);if(p.y<miny){miny=p.y;target=inputs[ii];}}target&&JX.DOM.focus(target);}catch(a){}}else if(this.getHandler()){this.getHandler()(c);this._e();}},_d:function(){if(!this._j){this._j=true;JX.Workflow._d(this);}},_e:function(){if(this._j){this._j=false;JX.Workflow._e();}},_f:function(){if(this._i){JX.DOM.remove(this._i);this._i=null;}},start:function(){var c=this.getURI();var a=this.getMethod();var b=new JX.Request(c,JX.bind(this,this._k));b.setData(this.getData());b.setDataSerializer(this.getDataSerializer());if(a)b.setMethod(a);b.listen('finally',JX.bind(this,this.invoke,'finally'));b.listen('error',JX.bind(this,function(e){var d=this.invoke('error',e);if(d.getStopped())return;}));b.send();}},properties:{handler:null,closeHandler:null,data:null,dataSerializer:null,method:null,URI:null}});
 | 
			
		||||
		Reference in New Issue
	
	Block a user