Page MenuHomestyx hydra

No OneTemporary

diff --git a/resources/sql/patches/030.imagemacro.sql b/resources/sql/patches/030.imagemacro.sql
new file mode 100644
index 0000000000..8e90fc26d5
--- /dev/null
+++ b/resources/sql/patches/030.imagemacro.sql
@@ -0,0 +1,5 @@
+CREATE TABLE phabricator_file.`file_imagemacro` (
+ `id` int unsigned NOT NULL auto_increment PRIMARY KEY,
+ `filePHID` varchar(64) NOT NULL,
+ `name` varchar(255) NOT NULL
+);
diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php
index b3ec17f3d2..e5685d3268 100644
--- a/src/__phutil_library_map__.php
+++ b/src/__phutil_library_map__.php
@@ -1,816 +1,820 @@
<?php
/**
* This file is automatically generated. Use 'phutil_mapper.php' to rebuild it.
* @generated
*/
phutil_register_library_map(array(
'class' =>
array(
'Aphront400Response' => 'aphront/response/400',
'Aphront404Response' => 'aphront/response/404',
'AphrontAjaxResponse' => 'aphront/response/ajax',
'AphrontApplicationConfiguration' => 'aphront/applicationconfiguration',
'AphrontController' => 'aphront/controller',
'AphrontCrumbsView' => 'view/layout/crumbs',
'AphrontDatabaseConnection' => 'storage/connection/base',
'AphrontDefaultApplicationConfiguration' => 'aphront/default/configuration',
'AphrontDefaultApplicationController' => 'aphront/default/controller',
'AphrontDialogResponse' => 'aphront/response/dialog',
'AphrontDialogView' => 'view/dialog',
'AphrontErrorView' => 'view/form/error',
'AphrontException' => 'aphront/exception/base',
'AphrontFileResponse' => 'aphront/response/file',
'AphrontFormCheckboxControl' => 'view/form/control/checkbox',
'AphrontFormControl' => 'view/form/control/base',
'AphrontFormDividerControl' => 'view/form/control/divider',
'AphrontFormFileControl' => 'view/form/control/file',
'AphrontFormMarkupControl' => 'view/form/control/markup',
'AphrontFormPasswordControl' => 'view/form/control/password',
'AphrontFormRecaptchaControl' => 'view/form/control/recaptcha',
'AphrontFormSelectControl' => 'view/form/control/select',
'AphrontFormStaticControl' => 'view/form/control/static',
'AphrontFormSubmitControl' => 'view/form/control/submit',
'AphrontFormTextAreaControl' => 'view/form/control/textarea',
'AphrontFormTextControl' => 'view/form/control/text',
'AphrontFormToggleButtonsControl' => 'view/form/control/togglebuttons',
'AphrontFormTokenizerControl' => 'view/form/control/tokenizer',
'AphrontFormView' => 'view/form/base',
'AphrontHeadsupActionListView' => 'view/layout/headsup/actionlist',
'AphrontHeadsupActionView' => 'view/layout/headsup/action',
'AphrontListFilterView' => 'view/layout/listfilter',
'AphrontMySQLDatabaseConnection' => 'storage/connection/mysql',
'AphrontNullView' => 'view/null',
'AphrontPageView' => 'view/page/base',
'AphrontPagerView' => 'view/control/pager',
'AphrontPanelView' => 'view/layout/panel',
'AphrontQueryConnectionException' => 'storage/exception/connection',
'AphrontQueryConnectionLostException' => 'storage/exception/connectionlost',
'AphrontQueryCountException' => 'storage/exception/count',
'AphrontQueryDuplicateKeyException' => 'storage/exception/duplicatekey',
'AphrontQueryException' => 'storage/exception/base',
'AphrontQueryObjectMissingException' => 'storage/exception/objectmissing',
'AphrontQueryParameterException' => 'storage/exception/parameter',
'AphrontQueryRecoverableException' => 'storage/exception/recoverable',
'AphrontRedirectException' => 'aphront/exception/redirect',
'AphrontRedirectResponse' => 'aphront/response/redirect',
'AphrontRequest' => 'aphront/request',
'AphrontRequestFailureView' => 'view/page/failure',
'AphrontResponse' => 'aphront/response/base',
'AphrontSideNavView' => 'view/layout/sidenav',
'AphrontTableView' => 'view/control/table',
'AphrontTokenizerTemplateView' => 'view/control/tokenizer',
'AphrontTypeaheadTemplateView' => 'view/control/typeahead',
'AphrontURIMapper' => 'aphront/mapper',
'AphrontView' => 'view/base',
'AphrontWebpageResponse' => 'aphront/response/webpage',
'CelerityAPI' => 'infrastructure/celerity/api',
'CelerityResourceController' => 'infrastructure/celerity/controller',
'CelerityResourceMap' => 'infrastructure/celerity/map',
'CelerityStaticResourceResponse' => 'infrastructure/celerity/response',
'ConduitAPIMethod' => 'applications/conduit/method/base',
'ConduitAPIRequest' => 'applications/conduit/protocol/request',
'ConduitAPI_conduit_connect_Method' => 'applications/conduit/method/conduit/connect',
'ConduitAPI_conduit_ping_Method' => 'applications/conduit/method/conduit/ping',
'ConduitAPI_daemon_launched_Method' => 'applications/conduit/method/daemon/launched',
'ConduitAPI_daemon_log_Method' => 'applications/conduit/method/daemon/log',
'ConduitAPI_differential_creatediff_Method' => 'applications/conduit/method/differential/creatediff',
'ConduitAPI_differential_createrevision_Method' => 'applications/conduit/method/differential/createrevision',
'ConduitAPI_differential_find_Method' => 'applications/conduit/method/differential/find',
'ConduitAPI_differential_getcommitmessage_Method' => 'applications/conduit/method/differential/getcommitmessage',
'ConduitAPI_differential_getcommitpaths_Method' => 'applications/conduit/method/differential/getcommitpaths',
'ConduitAPI_differential_getdiff_Method' => 'applications/conduit/method/differential/getdiff',
'ConduitAPI_differential_markcommitted_Method' => 'applications/conduit/method/differential/markcommitted',
'ConduitAPI_differential_parsecommitmessage_Method' => 'applications/conduit/method/differential/parsecommitmessage',
'ConduitAPI_differential_setdiffproperty_Method' => 'applications/conduit/method/differential/setdiffproperty',
'ConduitAPI_differential_updaterevision_Method' => 'applications/conduit/method/differential/updaterevision',
'ConduitAPI_diffusion_getcommits_Method' => 'applications/conduit/method/diffusion/getcommits',
'ConduitAPI_file_upload_Method' => 'applications/conduit/method/file/upload',
'ConduitAPI_user_find_Method' => 'applications/conduit/method/user/find',
'ConduitAPI_user_whoami_Method' => 'applications/conduit/method/user/whoami',
'ConduitException' => 'applications/conduit/protocol/exception',
'DarkConsole' => 'aphront/console/api',
'DarkConsoleConfigPlugin' => 'aphront/console/plugin/config',
'DarkConsoleController' => 'aphront/console/controller',
'DarkConsoleCore' => 'aphront/console/core',
'DarkConsoleErrorLogPlugin' => 'aphront/console/plugin/errorlog',
'DarkConsoleErrorLogPluginAPI' => 'aphront/console/plugin/errorlog/api',
'DarkConsolePlugin' => 'aphront/console/plugin/base',
'DarkConsoleRequestPlugin' => 'aphront/console/plugin/request',
'DarkConsoleServicesPlugin' => 'aphront/console/plugin/services',
'DarkConsoleServicesPluginAPI' => 'aphront/console/plugin/services/api',
'DarkConsoleXHProfPlugin' => 'aphront/console/plugin/xhprof',
'DarkConsoleXHProfPluginAPI' => 'aphront/console/plugin/xhprof/api',
'DifferentialAction' => 'applications/differential/constants/action',
'DifferentialAddCommentView' => 'applications/differential/view/addcomment',
'DifferentialAttachController' => 'applications/differential/controller/attach',
'DifferentialCCWelcomeMail' => 'applications/differential/mail/ccwelcome',
'DifferentialChangeType' => 'applications/differential/constants/changetype',
'DifferentialChangeset' => 'applications/differential/storage/changeset',
'DifferentialChangesetDetailView' => 'applications/differential/view/changesetdetailview',
'DifferentialChangesetListView' => 'applications/differential/view/changesetlistview',
'DifferentialChangesetParser' => 'applications/differential/parser/changeset',
'DifferentialChangesetViewController' => 'applications/differential/controller/changesetview',
'DifferentialComment' => 'applications/differential/storage/comment',
'DifferentialCommentEditor' => 'applications/differential/editor/comment',
'DifferentialCommentMail' => 'applications/differential/mail/comment',
'DifferentialCommentPreviewController' => 'applications/differential/controller/commentpreview',
'DifferentialCommentSaveController' => 'applications/differential/controller/commentsave',
'DifferentialCommitMessage' => 'applications/differential/parser/commitmessage',
'DifferentialCommitMessageData' => 'applications/differential/data/commitmessage',
'DifferentialCommitMessageParserException' => 'applications/differential/parser/commitmessage/exception',
'DifferentialController' => 'applications/differential/controller/base',
'DifferentialDAO' => 'applications/differential/storage/base',
'DifferentialDiff' => 'applications/differential/storage/diff',
'DifferentialDiffContentMail' => 'applications/differential/mail/diffcontent',
'DifferentialDiffCreateController' => 'applications/differential/controller/diffcreate',
'DifferentialDiffProperty' => 'applications/differential/storage/diffproperty',
'DifferentialDiffTableOfContentsView' => 'applications/differential/view/difftableofcontents',
'DifferentialDiffViewController' => 'applications/differential/controller/diffview',
'DifferentialHunk' => 'applications/differential/storage/hunk',
'DifferentialInlineComment' => 'applications/differential/storage/inlinecomment',
'DifferentialInlineCommentEditController' => 'applications/differential/controller/inlinecommentedit',
'DifferentialInlineCommentPreviewController' => 'applications/differential/controller/inlinecommentpreview',
'DifferentialInlineCommentView' => 'applications/differential/view/inlinecomment',
'DifferentialLintStatus' => 'applications/differential/constants/lintstatus',
'DifferentialMail' => 'applications/differential/mail/base',
'DifferentialMarkupEngineFactory' => 'applications/differential/parser/markup',
'DifferentialNewDiffMail' => 'applications/differential/mail/newdiff',
'DifferentialReviewRequestMail' => 'applications/differential/mail/reviewrequest',
'DifferentialRevision' => 'applications/differential/storage/revision',
'DifferentialRevisionCommentListView' => 'applications/differential/view/revisioncommentlist',
'DifferentialRevisionCommentView' => 'applications/differential/view/revisioncomment',
'DifferentialRevisionControlSystem' => 'applications/differential/constants/revisioncontrolsystem',
'DifferentialRevisionDetailRenderer' => 'applications/differential/controller/customrenderer',
'DifferentialRevisionDetailView' => 'applications/differential/view/revisiondetail',
'DifferentialRevisionEditController' => 'applications/differential/controller/revisionedit',
'DifferentialRevisionEditor' => 'applications/differential/editor/revision',
'DifferentialRevisionListController' => 'applications/differential/controller/revisionlist',
'DifferentialRevisionListData' => 'applications/differential/data/revisionlist',
'DifferentialRevisionStatus' => 'applications/differential/constants/revisionstatus',
'DifferentialRevisionUpdateHistoryView' => 'applications/differential/view/revisionupdatehistory',
'DifferentialRevisionViewController' => 'applications/differential/controller/revisionview',
'DifferentialSubscribeController' => 'applications/differential/controller/subscribe',
'DifferentialUnitStatus' => 'applications/differential/constants/unitstatus',
'DiffusionBranchInformation' => 'applications/diffusion/data/branch',
'DiffusionBranchQuery' => 'applications/diffusion/query/branch/base',
'DiffusionBranchTableView' => 'applications/diffusion/view/branchtable',
'DiffusionBrowseController' => 'applications/diffusion/controller/browse',
'DiffusionBrowseFileController' => 'applications/diffusion/controller/file',
'DiffusionBrowseQuery' => 'applications/diffusion/query/browse/base',
'DiffusionBrowseTableView' => 'applications/diffusion/view/browsetable',
'DiffusionChangeController' => 'applications/diffusion/controller/change',
'DiffusionCommitChangeTableView' => 'applications/diffusion/view/commitchangetable',
'DiffusionCommitController' => 'applications/diffusion/controller/commit',
'DiffusionController' => 'applications/diffusion/controller/base',
'DiffusionDiffController' => 'applications/diffusion/controller/diff',
'DiffusionDiffQuery' => 'applications/diffusion/query/diff/base',
'DiffusionFileContent' => 'applications/diffusion/data/filecontent',
'DiffusionFileContentQuery' => 'applications/diffusion/query/filecontent/base',
'DiffusionGitBranchQuery' => 'applications/diffusion/query/branch/git',
'DiffusionGitBrowseQuery' => 'applications/diffusion/query/browse/git',
'DiffusionGitDiffQuery' => 'applications/diffusion/query/diff/git',
'DiffusionGitFileContentQuery' => 'applications/diffusion/query/filecontent/git',
'DiffusionGitHistoryQuery' => 'applications/diffusion/query/history/git',
'DiffusionGitLastModifiedQuery' => 'applications/diffusion/query/lastmodified/git',
'DiffusionGitPathIDQuery' => 'applications/diffusion/query/pathid/base',
'DiffusionGitRequest' => 'applications/diffusion/request/git',
'DiffusionHistoryController' => 'applications/diffusion/controller/history',
'DiffusionHistoryQuery' => 'applications/diffusion/query/history/base',
'DiffusionHistoryTableView' => 'applications/diffusion/view/historytable',
'DiffusionHomeController' => 'applications/diffusion/controller/home',
'DiffusionLastModifiedController' => 'applications/diffusion/controller/lastmodified',
'DiffusionLastModifiedQuery' => 'applications/diffusion/query/lastmodified/base',
'DiffusionPathChange' => 'applications/diffusion/data/pathchange',
'DiffusionPathChangeQuery' => 'applications/diffusion/query/pathchange/base',
'DiffusionPathCompleteController' => 'applications/diffusion/controller/pathcomplete',
'DiffusionPathValidateController' => 'applications/diffusion/controller/pathvalidate',
'DiffusionRepositoryController' => 'applications/diffusion/controller/repository',
'DiffusionRepositoryPath' => 'applications/diffusion/data/repositorypath',
'DiffusionRequest' => 'applications/diffusion/request/base',
'DiffusionSvnBrowseQuery' => 'applications/diffusion/query/browse/svn',
'DiffusionSvnDiffQuery' => 'applications/diffusion/query/diff/svn',
'DiffusionSvnFileContentQuery' => 'applications/diffusion/query/filecontent/svn',
'DiffusionSvnHistoryQuery' => 'applications/diffusion/query/history/svn',
'DiffusionSvnLastModifiedQuery' => 'applications/diffusion/query/lastmodified/svn',
'DiffusionSvnRequest' => 'applications/diffusion/request/svn',
'DiffusionView' => 'applications/diffusion/view/base',
'HeraldAction' => 'applications/herald/storage/action',
'HeraldActionConfig' => 'applications/herald/config/action',
'HeraldApplyTranscript' => 'applications/herald/storage/transcript/apply',
'HeraldCommitAdapter' => 'applications/herald/adapter/commit',
'HeraldCondition' => 'applications/herald/storage/condition',
'HeraldConditionConfig' => 'applications/herald/config/condition',
'HeraldConditionTranscript' => 'applications/herald/storage/transcript/condition',
'HeraldContentTypeConfig' => 'applications/herald/config/contenttype',
'HeraldController' => 'applications/herald/controller/base',
'HeraldDAO' => 'applications/herald/storage/base',
'HeraldDeleteController' => 'applications/herald/controller/delete',
'HeraldDifferentialRevisionAdapter' => 'applications/herald/adapter/differential',
'HeraldDryRunAdapter' => 'applications/herald/adapter/dryrun',
'HeraldEffect' => 'applications/herald/engine/effect',
'HeraldEngine' => 'applications/herald/engine/engine',
'HeraldFieldConfig' => 'applications/herald/config/field',
'HeraldHomeController' => 'applications/herald/controller/home',
'HeraldInvalidConditionException' => 'applications/herald/engine/engine/exception',
'HeraldInvalidFieldException' => 'applications/herald/engine/engine/exception',
'HeraldNewController' => 'applications/herald/controller/new',
'HeraldObjectAdapter' => 'applications/herald/adapter/base',
'HeraldObjectTranscript' => 'applications/herald/storage/transcript/object',
'HeraldRecursiveConditionsException' => 'applications/herald/engine/engine/exception',
'HeraldRule' => 'applications/herald/storage/rule',
'HeraldRuleController' => 'applications/herald/controller/rule',
'HeraldRuleTranscript' => 'applications/herald/storage/transcript/rule',
'HeraldTestConsoleController' => 'applications/herald/controller/test',
'HeraldTranscript' => 'applications/herald/storage/transcript/base',
'HeraldTranscriptController' => 'applications/herald/controller/transcript',
'HeraldTranscriptListController' => 'applications/herald/controller/transcriptlist',
'HeraldValueTypeConfig' => 'applications/herald/config/valuetype',
'Javelin' => 'infrastructure/javelin/api',
'LiskDAO' => 'storage/lisk/dao',
'ManiphestController' => 'applications/maniphest/controller/base',
'ManiphestDAO' => 'applications/maniphest/storage/base',
'ManiphestTask' => 'applications/maniphest/storage/task',
'ManiphestTaskDetailController' => 'applications/maniphest/controller/taskdetail',
'ManiphestTaskEditController' => 'applications/maniphest/controller/taskedit',
'ManiphestTaskListController' => 'applications/maniphest/controller/tasklist',
'ManiphestTaskListView' => 'applications/maniphest/view/tasklist',
'ManiphestTaskPriority' => 'applications/maniphest/constants/priority',
'ManiphestTaskSelectorSearchController' => 'applications/maniphest/controller/taskselectorsearch',
'ManiphestTaskStatus' => 'applications/maniphest/constants/status',
'ManiphestTaskSummaryView' => 'applications/maniphest/view/tasksummary',
'ManiphestTransaction' => 'applications/maniphest/storage/transaction',
'ManiphestTransactionDetailView' => 'applications/maniphest/view/transactiondetail',
'ManiphestTransactionEditor' => 'applications/maniphest/editor/transaction',
'ManiphestTransactionListView' => 'applications/maniphest/view/transactionlist',
'ManiphestTransactionSaveController' => 'applications/maniphest/controller/transactionsave',
'ManiphestTransactionType' => 'applications/maniphest/constants/transactiontype',
'Phabricator404Controller' => 'applications/base/controller/404',
'PhabricatorAuthController' => 'applications/auth/controller/base',
'PhabricatorConduitAPIController' => 'applications/conduit/controller/api',
'PhabricatorConduitConnectionLog' => 'applications/conduit/storage/connectionlog',
'PhabricatorConduitConsoleController' => 'applications/conduit/controller/console',
'PhabricatorConduitController' => 'applications/conduit/controller/base',
'PhabricatorConduitDAO' => 'applications/conduit/storage/base',
'PhabricatorConduitLogController' => 'applications/conduit/controller/log',
'PhabricatorConduitMethodCallLog' => 'applications/conduit/storage/methodcalllog',
'PhabricatorController' => 'applications/base/controller/base',
'PhabricatorDaemon' => 'infrastructure/daemon/base',
'PhabricatorDaemonConsoleController' => 'applications/daemon/controller/console',
'PhabricatorDaemonControl' => 'infrastructure/daemon/control',
'PhabricatorDaemonController' => 'applications/daemon/controller/base',
'PhabricatorDaemonDAO' => 'infrastructure/daemon/storage/base',
'PhabricatorDaemonLog' => 'infrastructure/daemon/storage/log',
'PhabricatorDaemonLogEvent' => 'infrastructure/daemon/storage/event',
'PhabricatorDaemonLogViewController' => 'applications/daemon/controller/logview',
'PhabricatorDaemonReference' => 'infrastructure/daemon/control/reference',
'PhabricatorDaemonTimelineConsoleController' => 'applications/daemon/controller/timeline',
'PhabricatorDaemonTimelineEventController' => 'applications/daemon/controller/timelineevent',
'PhabricatorDirectoryCategory' => 'applications/directory/storage/category',
'PhabricatorDirectoryCategoryDeleteController' => 'applications/directory/controller/categorydelete',
'PhabricatorDirectoryCategoryEditController' => 'applications/directory/controller/categoryedit',
'PhabricatorDirectoryCategoryListController' => 'applications/directory/controller/categorylist',
'PhabricatorDirectoryController' => 'applications/directory/controller/base',
'PhabricatorDirectoryDAO' => 'applications/directory/storage/base',
'PhabricatorDirectoryItem' => 'applications/directory/storage/item',
'PhabricatorDirectoryItemDeleteController' => 'applications/directory/controller/itemdelete',
'PhabricatorDirectoryItemEditController' => 'applications/directory/controller/itemedit',
'PhabricatorDirectoryItemListController' => 'applications/directory/controller/itemlist',
'PhabricatorDirectoryMainController' => 'applications/directory/controller/main',
'PhabricatorDraft' => 'applications/draft/storage/draft',
'PhabricatorDraftDAO' => 'applications/draft/storage/base',
'PhabricatorEditPreferencesController' => 'applications/preferences/controller/edit',
'PhabricatorEmailLoginController' => 'applications/auth/controller/email',
'PhabricatorEmailTokenController' => 'applications/auth/controller/emailtoken',
'PhabricatorEnv' => 'infrastructure/env',
'PhabricatorFile' => 'applications/files/storage/file',
'PhabricatorFileController' => 'applications/files/controller/base',
'PhabricatorFileDAO' => 'applications/files/storage/base',
+ 'PhabricatorFileImageMacro' => 'applications/files/storage/imagemacro',
'PhabricatorFileListController' => 'applications/files/controller/list',
'PhabricatorFileStorageBlob' => 'applications/files/storage/storageblob',
'PhabricatorFileURI' => 'applications/files/uri',
'PhabricatorFileUploadController' => 'applications/files/controller/upload',
'PhabricatorFileViewController' => 'applications/files/controller/view',
'PhabricatorGoodForNothingWorker' => 'infrastructure/daemon/workers/worker/goodfornothing',
'PhabricatorHandleObjectSelectorDataView' => 'applications/phid/handle/view/selector',
'PhabricatorLiskDAO' => 'applications/base/storage/lisk',
'PhabricatorLoginController' => 'applications/auth/controller/login',
'PhabricatorLogoutController' => 'applications/auth/controller/logout',
'PhabricatorMailImplementationAdapter' => 'applications/metamta/adapter/base',
'PhabricatorMailImplementationAmazonSESAdapter' => 'applications/metamta/adapter/amazonses',
'PhabricatorMailImplementationPHPMailerLiteAdapter' => 'applications/metamta/adapter/phpmailerlite',
'PhabricatorMetaMTAController' => 'applications/metamta/controller/base',
'PhabricatorMetaMTADAO' => 'applications/metamta/storage/base',
'PhabricatorMetaMTADaemon' => 'applications/metamta/daemon/mta',
'PhabricatorMetaMTAListController' => 'applications/metamta/controller/list',
'PhabricatorMetaMTAMail' => 'applications/metamta/storage/mail',
'PhabricatorMetaMTAMailingList' => 'applications/metamta/storage/mailinglist',
'PhabricatorMetaMTAMailingListEditController' => 'applications/metamta/controller/mailinglistedit',
'PhabricatorMetaMTAMailingListsController' => 'applications/metamta/controller/mailinglists',
'PhabricatorMetaMTASendController' => 'applications/metamta/controller/send',
'PhabricatorMetaMTAViewController' => 'applications/metamta/controller/view',
'PhabricatorOAuthDefaultRegistrationController' => 'applications/auth/controller/oauthregistration/default',
'PhabricatorOAuthDiagnosticsController' => 'applications/auth/controller/oauthdiagnostics',
'PhabricatorOAuthFailureView' => 'applications/auth/view/oauthfailure',
'PhabricatorOAuthLoginController' => 'applications/auth/controller/oauth',
'PhabricatorOAuthProvider' => 'applications/auth/oauth/provider/base',
'PhabricatorOAuthProviderFacebook' => 'applications/auth/oauth/provider/facebook',
'PhabricatorOAuthProviderGithub' => 'applications/auth/oauth/provider/github',
'PhabricatorOAuthRegistrationController' => 'applications/auth/controller/oauthregistration/base',
'PhabricatorOAuthUnlinkController' => 'applications/auth/controller/unlink',
'PhabricatorObjectHandle' => 'applications/phid/handle',
'PhabricatorObjectHandleData' => 'applications/phid/handle/data',
'PhabricatorObjectSelectorDialog' => 'view/control/objectselector',
'PhabricatorOwnersController' => 'applications/owners/controller/base',
'PhabricatorOwnersDAO' => 'applications/owners/storage/base',
'PhabricatorOwnersDeleteController' => 'applications/owners/controller/delete',
'PhabricatorOwnersDetailController' => 'applications/owners/controller/detail',
'PhabricatorOwnersEditController' => 'applications/owners/controller/edit',
'PhabricatorOwnersListController' => 'applications/owners/controller/list',
'PhabricatorOwnersOwner' => 'applications/owners/storage/owner',
'PhabricatorOwnersPackage' => 'applications/owners/storage/package',
'PhabricatorOwnersPath' => 'applications/owners/storage/path',
'PhabricatorPHID' => 'applications/phid/storage/phid',
'PhabricatorPHIDAllocateController' => 'applications/phid/controller/allocate',
'PhabricatorPHIDConstants' => 'applications/phid/constants',
'PhabricatorPHIDController' => 'applications/phid/controller/base',
'PhabricatorPHIDDAO' => 'applications/phid/storage/base',
'PhabricatorPHIDListController' => 'applications/phid/controller/list',
'PhabricatorPHIDLookupController' => 'applications/phid/controller/lookup',
'PhabricatorPeopleController' => 'applications/people/controller/base',
'PhabricatorPeopleEditController' => 'applications/people/controller/edit',
'PhabricatorPeopleListController' => 'applications/people/controller/list',
'PhabricatorPeopleProfileController' => 'applications/people/controller/profile',
'PhabricatorPeopleProfileEditController' => 'applications/people/controller/profileedit',
'PhabricatorPreferencesController' => 'applications/preferences/controller/base',
'PhabricatorProject' => 'applications/project/storage/project',
'PhabricatorProjectAffiliation' => 'applications/project/storage/affiliation',
'PhabricatorProjectAffiliationEditController' => 'applications/project/controller/editaffiliation',
'PhabricatorProjectController' => 'applications/project/controller/base',
'PhabricatorProjectDAO' => 'applications/project/storage/base',
'PhabricatorProjectEditController' => 'applications/project/controller/edit',
'PhabricatorProjectListController' => 'applications/project/controller/list',
'PhabricatorProjectProfile' => 'applications/project/storage/profile',
'PhabricatorProjectProfileController' => 'applications/project/controller/profile',
'PhabricatorRedirectController' => 'applications/base/controller/redirect',
'PhabricatorRemarkupRuleDifferential' => 'infrastructure/markup/remarkup/markuprule/differential',
'PhabricatorRemarkupRuleDiffusion' => 'infrastructure/markup/remarkup/markuprule/diffusion',
+ 'PhabricatorRemarkupRuleImageMacro' => 'infrastructure/markup/remarkup/markuprule/imagemacro',
'PhabricatorRemarkupRuleManiphest' => 'infrastructure/markup/remarkup/markuprule/maniphest',
'PhabricatorRepository' => 'applications/repository/storage/repository',
'PhabricatorRepositoryArcanistProject' => 'applications/repository/storage/arcanistproject',
'PhabricatorRepositoryArcanistProjectEditController' => 'applications/repository/controller/arcansistprojectedit',
'PhabricatorRepositoryCommit' => 'applications/repository/storage/commit',
'PhabricatorRepositoryCommitChangeParserWorker' => 'applications/repository/worker/commitchangeparser/base',
'PhabricatorRepositoryCommitData' => 'applications/repository/storage/commitdata',
'PhabricatorRepositoryCommitDiscoveryDaemon' => 'applications/repository/daemon/commitdiscovery/base',
'PhabricatorRepositoryCommitHeraldWorker' => 'applications/repository/worker/herald',
'PhabricatorRepositoryCommitMessageDetailParser' => 'applications/repository/parser/base',
'PhabricatorRepositoryCommitMessageParserWorker' => 'applications/repository/worker/commitmessageparser/base',
'PhabricatorRepositoryCommitParserWorker' => 'applications/repository/worker/base',
'PhabricatorRepositoryCommitTaskDaemon' => 'applications/repository/daemon/committask',
'PhabricatorRepositoryController' => 'applications/repository/controller/base',
'PhabricatorRepositoryCreateController' => 'applications/repository/controller/create',
'PhabricatorRepositoryDAO' => 'applications/repository/storage/base',
'PhabricatorRepositoryDaemon' => 'applications/repository/daemon/base',
'PhabricatorRepositoryDefaultCommitMessageDetailParser' => 'applications/repository/parser/default',
'PhabricatorRepositoryEditController' => 'applications/repository/controller/edit',
'PhabricatorRepositoryGitCommitChangeParserWorker' => 'applications/repository/worker/commitchangeparser/git',
'PhabricatorRepositoryGitCommitDiscoveryDaemon' => 'applications/repository/daemon/commitdiscovery/git',
'PhabricatorRepositoryGitCommitMessageParserWorker' => 'applications/repository/worker/commitmessageparser/git',
'PhabricatorRepositoryGitFetchDaemon' => 'applications/repository/daemon/gitfetch',
'PhabricatorRepositoryGitHubNotification' => 'applications/repository/storage/githubnotification',
'PhabricatorRepositoryGitHubPostReceiveController' => 'applications/repository/controller/github-post-receive',
'PhabricatorRepositoryListController' => 'applications/repository/controller/list',
'PhabricatorRepositoryShortcut' => 'applications/repository/storage/shortcut',
'PhabricatorRepositorySvnCommitChangeParserWorker' => 'applications/repository/worker/commitchangeparser/svn',
'PhabricatorRepositorySvnCommitDiscoveryDaemon' => 'applications/repository/daemon/commitdiscovery/svn',
'PhabricatorRepositorySvnCommitMessageParserWorker' => 'applications/repository/worker/commitmessageparser/svn',
'PhabricatorRepositoryType' => 'applications/repository/constants/repositorytype',
'PhabricatorSearchAbstractDocument' => 'applications/search/index/abstractdocument',
'PhabricatorSearchBaseController' => 'applications/search/controller/base',
'PhabricatorSearchController' => 'applications/search/controller/search',
'PhabricatorSearchDAO' => 'applications/search/storage/base',
'PhabricatorSearchDifferentialIndexer' => 'applications/search/index/indexer/differential',
'PhabricatorSearchDocument' => 'applications/search/storage/document/document',
'PhabricatorSearchDocumentField' => 'applications/search/storage/document/field',
'PhabricatorSearchDocumentIndexer' => 'applications/search/index/indexer/base',
'PhabricatorSearchDocumentRelationship' => 'applications/search/storage/document/relationship',
'PhabricatorSearchExecutor' => 'applications/search/execute/base',
'PhabricatorSearchField' => 'applications/search/constants/field',
'PhabricatorSearchManiphestIndexer' => 'applications/search/index/indexer/maniphest',
'PhabricatorSearchMySQLExecutor' => 'applications/search/execute/mysql',
'PhabricatorSearchQuery' => 'applications/search/storage/query',
'PhabricatorSearchRelationship' => 'applications/search/constants/relationship',
'PhabricatorStandardPageView' => 'view/page/standard',
'PhabricatorStatusController' => 'applications/status/base',
'PhabricatorTaskmasterDaemon' => 'infrastructure/daemon/workers/taskmaster',
'PhabricatorTimelineCursor' => 'infrastructure/daemon/timeline/storage/cursor',
'PhabricatorTimelineDAO' => 'infrastructure/daemon/timeline/storage/base',
'PhabricatorTimelineEvent' => 'infrastructure/daemon/timeline/storage/event',
'PhabricatorTimelineEventData' => 'infrastructure/daemon/timeline/storage/eventdata',
'PhabricatorTimelineIterator' => 'infrastructure/daemon/timeline/cursor/iterator',
'PhabricatorTypeaheadCommonDatasourceController' => 'applications/typeahead/controller/common',
'PhabricatorTypeaheadDatasourceController' => 'applications/typeahead/controller/base',
'PhabricatorUIExample' => 'applications/uiexample/examples/base',
'PhabricatorUIExampleController' => 'applications/uiexample/controller/base',
'PhabricatorUIExampleRenderController' => 'applications/uiexample/controller/render',
'PhabricatorUIListFilterExample' => 'applications/uiexample/examples/listfilter',
'PhabricatorUIPagerExample' => 'applications/uiexample/examples/pager',
'PhabricatorUser' => 'applications/people/storage/user',
'PhabricatorUserDAO' => 'applications/people/storage/base',
'PhabricatorUserOAuthInfo' => 'applications/people/storage/useroauthinfo',
'PhabricatorUserPreferences' => 'applications/people/storage/preferences',
'PhabricatorUserProfile' => 'applications/people/storage/profile',
'PhabricatorUserSettingsController' => 'applications/people/controller/settings',
'PhabricatorWorker' => 'infrastructure/daemon/workers/worker',
'PhabricatorWorkerDAO' => 'infrastructure/daemon/workers/storage/base',
'PhabricatorWorkerTask' => 'infrastructure/daemon/workers/storage/task',
'PhabricatorWorkerTaskData' => 'infrastructure/daemon/workers/storage/taskdata',
'PhabricatorWorkerTaskDetailController' => 'applications/daemon/controller/workertaskdetail',
'PhabricatorXHPASTViewController' => 'applications/xhpastview/controller/base',
'PhabricatorXHPASTViewDAO' => 'applications/xhpastview/storage/base',
'PhabricatorXHPASTViewFrameController' => 'applications/xhpastview/controller/viewframe',
'PhabricatorXHPASTViewFramesetController' => 'applications/xhpastview/controller/viewframeset',
'PhabricatorXHPASTViewInputController' => 'applications/xhpastview/controller/viewinput',
'PhabricatorXHPASTViewPanelController' => 'applications/xhpastview/controller/viewpanel',
'PhabricatorXHPASTViewParseTree' => 'applications/xhpastview/storage/parsetree',
'PhabricatorXHPASTViewRunController' => 'applications/xhpastview/controller/run',
'PhabricatorXHPASTViewStreamController' => 'applications/xhpastview/controller/viewstream',
'PhabricatorXHPASTViewTreeController' => 'applications/xhpastview/controller/viewtree',
'PhabricatorXHProfController' => 'applications/xhprof/controller/base',
'PhabricatorXHProfProfileController' => 'applications/xhprof/controller/profile',
'PhabricatorXHProfProfileSymbolView' => 'applications/xhprof/view/symbol',
'PhabricatorXHProfProfileTopLevelView' => 'applications/xhprof/view/toplevel',
),
'function' =>
array(
'_qsprintf_check_scalar_type' => 'storage/qsprintf',
'_qsprintf_check_type' => 'storage/qsprintf',
'celerity_generate_unique_node_id' => 'infrastructure/celerity/api',
'celerity_register_resource_map' => 'infrastructure/celerity/map',
'javelin_render_tag' => 'infrastructure/javelin/markup',
'phabricator_format_relative_time' => 'view/utils',
'phabricator_format_timestamp' => 'view/utils',
'phabricator_format_units_generic' => 'view/utils',
'phabricator_render_form' => 'infrastructure/javelin/markup',
'qsprintf' => 'storage/qsprintf',
'queryfx' => 'storage/queryfx',
'queryfx_all' => 'storage/queryfx',
'queryfx_one' => 'storage/queryfx',
'require_celerity_resource' => 'infrastructure/celerity/api',
'vqsprintf' => 'storage/qsprintf',
'vqueryfx' => 'storage/queryfx',
'vqueryfx_all' => 'storage/queryfx',
'xsprintf_query' => 'storage/qsprintf',
),
'requires_class' =>
array(
'Aphront400Response' => 'AphrontResponse',
'Aphront404Response' => 'AphrontResponse',
'AphrontAjaxResponse' => 'AphrontResponse',
'AphrontCrumbsView' => 'AphrontView',
'AphrontDefaultApplicationConfiguration' => 'AphrontApplicationConfiguration',
'AphrontDefaultApplicationController' => 'AphrontController',
'AphrontDialogResponse' => 'AphrontResponse',
'AphrontDialogView' => 'AphrontView',
'AphrontErrorView' => 'AphrontView',
'AphrontFileResponse' => 'AphrontResponse',
'AphrontFormCheckboxControl' => 'AphrontFormControl',
'AphrontFormControl' => 'AphrontView',
'AphrontFormDividerControl' => 'AphrontFormControl',
'AphrontFormFileControl' => 'AphrontFormControl',
'AphrontFormMarkupControl' => 'AphrontFormControl',
'AphrontFormPasswordControl' => 'AphrontFormControl',
'AphrontFormRecaptchaControl' => 'AphrontFormControl',
'AphrontFormSelectControl' => 'AphrontFormControl',
'AphrontFormStaticControl' => 'AphrontFormControl',
'AphrontFormSubmitControl' => 'AphrontFormControl',
'AphrontFormTextAreaControl' => 'AphrontFormControl',
'AphrontFormTextControl' => 'AphrontFormControl',
'AphrontFormToggleButtonsControl' => 'AphrontFormControl',
'AphrontFormTokenizerControl' => 'AphrontFormControl',
'AphrontFormView' => 'AphrontView',
'AphrontHeadsupActionListView' => 'AphrontView',
'AphrontHeadsupActionView' => 'AphrontView',
'AphrontListFilterView' => 'AphrontView',
'AphrontMySQLDatabaseConnection' => 'AphrontDatabaseConnection',
'AphrontNullView' => 'AphrontView',
'AphrontPageView' => 'AphrontView',
'AphrontPagerView' => 'AphrontView',
'AphrontPanelView' => 'AphrontView',
'AphrontQueryConnectionException' => 'AphrontQueryException',
'AphrontQueryConnectionLostException' => 'AphrontQueryRecoverableException',
'AphrontQueryCountException' => 'AphrontQueryException',
'AphrontQueryDuplicateKeyException' => 'AphrontQueryException',
'AphrontQueryObjectMissingException' => 'AphrontQueryException',
'AphrontQueryParameterException' => 'AphrontQueryException',
'AphrontQueryRecoverableException' => 'AphrontQueryException',
'AphrontRedirectException' => 'AphrontException',
'AphrontRedirectResponse' => 'AphrontResponse',
'AphrontRequestFailureView' => 'AphrontView',
'AphrontSideNavView' => 'AphrontView',
'AphrontTableView' => 'AphrontView',
'AphrontTokenizerTemplateView' => 'AphrontView',
'AphrontTypeaheadTemplateView' => 'AphrontView',
'AphrontWebpageResponse' => 'AphrontResponse',
'CelerityResourceController' => 'AphrontController',
'ConduitAPI_conduit_connect_Method' => 'ConduitAPIMethod',
'ConduitAPI_conduit_ping_Method' => 'ConduitAPIMethod',
'ConduitAPI_daemon_launched_Method' => 'ConduitAPIMethod',
'ConduitAPI_daemon_log_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_creatediff_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_createrevision_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_find_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_getcommitmessage_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_getcommitpaths_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_getdiff_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_markcommitted_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_parsecommitmessage_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_setdiffproperty_Method' => 'ConduitAPIMethod',
'ConduitAPI_differential_updaterevision_Method' => 'ConduitAPIMethod',
'ConduitAPI_diffusion_getcommits_Method' => 'ConduitAPIMethod',
'ConduitAPI_file_upload_Method' => 'ConduitAPIMethod',
'ConduitAPI_user_find_Method' => 'ConduitAPIMethod',
'ConduitAPI_user_whoami_Method' => 'ConduitAPIMethod',
'DarkConsoleConfigPlugin' => 'DarkConsolePlugin',
'DarkConsoleController' => 'PhabricatorController',
'DarkConsoleErrorLogPlugin' => 'DarkConsolePlugin',
'DarkConsoleRequestPlugin' => 'DarkConsolePlugin',
'DarkConsoleServicesPlugin' => 'DarkConsolePlugin',
'DarkConsoleXHProfPlugin' => 'DarkConsolePlugin',
'DifferentialAddCommentView' => 'AphrontView',
'DifferentialAttachController' => 'DifferentialController',
'DifferentialCCWelcomeMail' => 'DifferentialReviewRequestMail',
'DifferentialChangeset' => 'DifferentialDAO',
'DifferentialChangesetDetailView' => 'AphrontView',
'DifferentialChangesetListView' => 'AphrontView',
'DifferentialChangesetViewController' => 'DifferentialController',
'DifferentialComment' => 'DifferentialDAO',
'DifferentialCommentMail' => 'DifferentialMail',
'DifferentialCommentPreviewController' => 'DifferentialController',
'DifferentialCommentSaveController' => 'DifferentialController',
'DifferentialController' => 'PhabricatorController',
'DifferentialDAO' => 'PhabricatorLiskDAO',
'DifferentialDiff' => 'DifferentialDAO',
'DifferentialDiffContentMail' => 'DifferentialMail',
'DifferentialDiffCreateController' => 'DifferentialController',
'DifferentialDiffProperty' => 'DifferentialDAO',
'DifferentialDiffTableOfContentsView' => 'AphrontView',
'DifferentialDiffViewController' => 'DifferentialController',
'DifferentialHunk' => 'DifferentialDAO',
'DifferentialInlineComment' => 'DifferentialDAO',
'DifferentialInlineCommentEditController' => 'DifferentialController',
'DifferentialInlineCommentPreviewController' => 'DifferentialController',
'DifferentialInlineCommentView' => 'AphrontView',
'DifferentialNewDiffMail' => 'DifferentialReviewRequestMail',
'DifferentialReviewRequestMail' => 'DifferentialMail',
'DifferentialRevision' => 'DifferentialDAO',
'DifferentialRevisionCommentListView' => 'AphrontView',
'DifferentialRevisionCommentView' => 'AphrontView',
'DifferentialRevisionDetailView' => 'AphrontView',
'DifferentialRevisionEditController' => 'DifferentialController',
'DifferentialRevisionListController' => 'DifferentialController',
'DifferentialRevisionUpdateHistoryView' => 'AphrontView',
'DifferentialRevisionViewController' => 'DifferentialController',
'DifferentialSubscribeController' => 'DifferentialController',
'DiffusionBranchTableView' => 'DiffusionView',
'DiffusionBrowseController' => 'DiffusionController',
'DiffusionBrowseFileController' => 'DiffusionController',
'DiffusionBrowseTableView' => 'DiffusionView',
'DiffusionChangeController' => 'DiffusionController',
'DiffusionCommitChangeTableView' => 'DiffusionView',
'DiffusionCommitController' => 'DiffusionController',
'DiffusionController' => 'PhabricatorController',
'DiffusionDiffController' => 'DiffusionController',
'DiffusionGitBranchQuery' => 'DiffusionBranchQuery',
'DiffusionGitBrowseQuery' => 'DiffusionBrowseQuery',
'DiffusionGitDiffQuery' => 'DiffusionDiffQuery',
'DiffusionGitFileContentQuery' => 'DiffusionFileContentQuery',
'DiffusionGitHistoryQuery' => 'DiffusionHistoryQuery',
'DiffusionGitLastModifiedQuery' => 'DiffusionLastModifiedQuery',
'DiffusionGitRequest' => 'DiffusionRequest',
'DiffusionHistoryController' => 'DiffusionController',
'DiffusionHistoryTableView' => 'DiffusionView',
'DiffusionHomeController' => 'DiffusionController',
'DiffusionLastModifiedController' => 'DiffusionController',
'DiffusionPathCompleteController' => 'DiffusionController',
'DiffusionPathValidateController' => 'DiffusionController',
'DiffusionRepositoryController' => 'DiffusionController',
'DiffusionSvnBrowseQuery' => 'DiffusionBrowseQuery',
'DiffusionSvnDiffQuery' => 'DiffusionDiffQuery',
'DiffusionSvnFileContentQuery' => 'DiffusionFileContentQuery',
'DiffusionSvnHistoryQuery' => 'DiffusionHistoryQuery',
'DiffusionSvnLastModifiedQuery' => 'DiffusionLastModifiedQuery',
'DiffusionSvnRequest' => 'DiffusionRequest',
'DiffusionView' => 'AphrontView',
'HeraldAction' => 'HeraldDAO',
'HeraldApplyTranscript' => 'HeraldDAO',
'HeraldCommitAdapter' => 'HeraldObjectAdapter',
'HeraldCondition' => 'HeraldDAO',
'HeraldController' => 'PhabricatorController',
'HeraldDAO' => 'PhabricatorLiskDAO',
'HeraldDeleteController' => 'HeraldController',
'HeraldDifferentialRevisionAdapter' => 'HeraldObjectAdapter',
'HeraldDryRunAdapter' => 'HeraldObjectAdapter',
'HeraldHomeController' => 'HeraldController',
'HeraldNewController' => 'HeraldController',
'HeraldRule' => 'HeraldDAO',
'HeraldRuleController' => 'HeraldController',
'HeraldTestConsoleController' => 'HeraldController',
'HeraldTranscript' => 'HeraldDAO',
'HeraldTranscriptController' => 'HeraldController',
'HeraldTranscriptListController' => 'HeraldController',
'ManiphestController' => 'PhabricatorController',
'ManiphestDAO' => 'PhabricatorLiskDAO',
'ManiphestTask' => 'ManiphestDAO',
'ManiphestTaskDetailController' => 'ManiphestController',
'ManiphestTaskEditController' => 'ManiphestController',
'ManiphestTaskListController' => 'ManiphestController',
'ManiphestTaskListView' => 'AphrontView',
'ManiphestTaskSelectorSearchController' => 'ManiphestController',
'ManiphestTaskSummaryView' => 'AphrontView',
'ManiphestTransaction' => 'ManiphestDAO',
'ManiphestTransactionDetailView' => 'AphrontView',
'ManiphestTransactionListView' => 'AphrontView',
'ManiphestTransactionSaveController' => 'ManiphestController',
'Phabricator404Controller' => 'PhabricatorController',
'PhabricatorAuthController' => 'PhabricatorController',
'PhabricatorConduitAPIController' => 'PhabricatorConduitController',
'PhabricatorConduitConnectionLog' => 'PhabricatorConduitDAO',
'PhabricatorConduitConsoleController' => 'PhabricatorConduitController',
'PhabricatorConduitController' => 'PhabricatorController',
'PhabricatorConduitDAO' => 'PhabricatorLiskDAO',
'PhabricatorConduitLogController' => 'PhabricatorConduitController',
'PhabricatorConduitMethodCallLog' => 'PhabricatorConduitDAO',
'PhabricatorController' => 'AphrontController',
'PhabricatorDaemon' => 'PhutilDaemon',
'PhabricatorDaemonConsoleController' => 'PhabricatorDaemonController',
'PhabricatorDaemonController' => 'PhabricatorController',
'PhabricatorDaemonDAO' => 'PhabricatorLiskDAO',
'PhabricatorDaemonLog' => 'PhabricatorDaemonDAO',
'PhabricatorDaemonLogEvent' => 'PhabricatorDaemonDAO',
'PhabricatorDaemonLogViewController' => 'PhabricatorDaemonController',
'PhabricatorDaemonTimelineConsoleController' => 'PhabricatorDaemonController',
'PhabricatorDaemonTimelineEventController' => 'PhabricatorDaemonController',
'PhabricatorDirectoryCategory' => 'PhabricatorDirectoryDAO',
'PhabricatorDirectoryCategoryDeleteController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryCategoryEditController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryCategoryListController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryController' => 'PhabricatorController',
'PhabricatorDirectoryDAO' => 'PhabricatorLiskDAO',
'PhabricatorDirectoryItem' => 'PhabricatorDirectoryDAO',
'PhabricatorDirectoryItemDeleteController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryItemEditController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryItemListController' => 'PhabricatorDirectoryController',
'PhabricatorDirectoryMainController' => 'PhabricatorDirectoryController',
'PhabricatorDraft' => 'PhabricatorDraftDAO',
'PhabricatorDraftDAO' => 'PhabricatorLiskDAO',
'PhabricatorEditPreferencesController' => 'PhabricatorPreferencesController',
'PhabricatorEmailLoginController' => 'PhabricatorAuthController',
'PhabricatorEmailTokenController' => 'PhabricatorAuthController',
'PhabricatorFile' => 'PhabricatorFileDAO',
'PhabricatorFileController' => 'PhabricatorController',
'PhabricatorFileDAO' => 'PhabricatorLiskDAO',
+ 'PhabricatorFileImageMacro' => 'PhabricatorFileDAO',
'PhabricatorFileListController' => 'PhabricatorFileController',
'PhabricatorFileStorageBlob' => 'PhabricatorFileDAO',
'PhabricatorFileUploadController' => 'PhabricatorFileController',
'PhabricatorFileViewController' => 'PhabricatorFileController',
'PhabricatorGoodForNothingWorker' => 'PhabricatorWorker',
'PhabricatorLiskDAO' => 'LiskDAO',
'PhabricatorLoginController' => 'PhabricatorAuthController',
'PhabricatorLogoutController' => 'PhabricatorAuthController',
'PhabricatorMailImplementationAmazonSESAdapter' => 'PhabricatorMailImplementationPHPMailerLiteAdapter',
'PhabricatorMailImplementationPHPMailerLiteAdapter' => 'PhabricatorMailImplementationAdapter',
'PhabricatorMetaMTAController' => 'PhabricatorController',
'PhabricatorMetaMTADAO' => 'PhabricatorLiskDAO',
'PhabricatorMetaMTADaemon' => 'PhabricatorDaemon',
'PhabricatorMetaMTAListController' => 'PhabricatorMetaMTAController',
'PhabricatorMetaMTAMail' => 'PhabricatorMetaMTADAO',
'PhabricatorMetaMTAMailingList' => 'PhabricatorMetaMTADAO',
'PhabricatorMetaMTAMailingListEditController' => 'PhabricatorMetaMTAController',
'PhabricatorMetaMTAMailingListsController' => 'PhabricatorMetaMTAController',
'PhabricatorMetaMTASendController' => 'PhabricatorMetaMTAController',
'PhabricatorMetaMTAViewController' => 'PhabricatorMetaMTAController',
'PhabricatorOAuthDefaultRegistrationController' => 'PhabricatorOAuthRegistrationController',
'PhabricatorOAuthDiagnosticsController' => 'PhabricatorAuthController',
'PhabricatorOAuthFailureView' => 'AphrontView',
'PhabricatorOAuthLoginController' => 'PhabricatorAuthController',
'PhabricatorOAuthProviderFacebook' => 'PhabricatorOAuthProvider',
'PhabricatorOAuthProviderGithub' => 'PhabricatorOAuthProvider',
'PhabricatorOAuthRegistrationController' => 'PhabricatorAuthController',
'PhabricatorOAuthUnlinkController' => 'PhabricatorAuthController',
'PhabricatorOwnersController' => 'PhabricatorController',
'PhabricatorOwnersDAO' => 'PhabricatorLiskDAO',
'PhabricatorOwnersDeleteController' => 'PhabricatorOwnersController',
'PhabricatorOwnersDetailController' => 'PhabricatorOwnersController',
'PhabricatorOwnersEditController' => 'PhabricatorOwnersController',
'PhabricatorOwnersListController' => 'PhabricatorOwnersController',
'PhabricatorOwnersOwner' => 'PhabricatorOwnersDAO',
'PhabricatorOwnersPackage' => 'PhabricatorOwnersDAO',
'PhabricatorOwnersPath' => 'PhabricatorOwnersDAO',
'PhabricatorPHID' => 'PhabricatorPHIDDAO',
'PhabricatorPHIDAllocateController' => 'PhabricatorPHIDController',
'PhabricatorPHIDController' => 'PhabricatorController',
'PhabricatorPHIDDAO' => 'PhabricatorLiskDAO',
'PhabricatorPHIDListController' => 'PhabricatorPHIDController',
'PhabricatorPHIDLookupController' => 'PhabricatorPHIDController',
'PhabricatorPeopleController' => 'PhabricatorController',
'PhabricatorPeopleEditController' => 'PhabricatorPeopleController',
'PhabricatorPeopleListController' => 'PhabricatorPeopleController',
'PhabricatorPeopleProfileController' => 'PhabricatorPeopleController',
'PhabricatorPeopleProfileEditController' => 'PhabricatorPeopleController',
'PhabricatorPreferencesController' => 'PhabricatorController',
'PhabricatorProject' => 'PhabricatorProjectDAO',
'PhabricatorProjectAffiliation' => 'PhabricatorProjectDAO',
'PhabricatorProjectAffiliationEditController' => 'PhabricatorProjectController',
'PhabricatorProjectController' => 'PhabricatorController',
'PhabricatorProjectDAO' => 'PhabricatorLiskDAO',
'PhabricatorProjectEditController' => 'PhabricatorProjectController',
'PhabricatorProjectListController' => 'PhabricatorProjectController',
'PhabricatorProjectProfile' => 'PhabricatorProjectDAO',
'PhabricatorProjectProfileController' => 'PhabricatorProjectController',
'PhabricatorRedirectController' => 'PhabricatorController',
'PhabricatorRemarkupRuleDifferential' => 'PhutilRemarkupRule',
'PhabricatorRemarkupRuleDiffusion' => 'PhutilRemarkupRule',
+ 'PhabricatorRemarkupRuleImageMacro' => 'PhutilRemarkupRule',
'PhabricatorRemarkupRuleManiphest' => 'PhutilRemarkupRule',
'PhabricatorRepository' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositoryArcanistProject' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositoryArcanistProjectEditController' => 'PhabricatorRepositoryController',
'PhabricatorRepositoryCommit' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositoryCommitChangeParserWorker' => 'PhabricatorRepositoryCommitParserWorker',
'PhabricatorRepositoryCommitData' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositoryCommitDiscoveryDaemon' => 'PhabricatorRepositoryDaemon',
'PhabricatorRepositoryCommitHeraldWorker' => 'PhabricatorRepositoryCommitParserWorker',
'PhabricatorRepositoryCommitMessageParserWorker' => 'PhabricatorRepositoryCommitParserWorker',
'PhabricatorRepositoryCommitParserWorker' => 'PhabricatorWorker',
'PhabricatorRepositoryCommitTaskDaemon' => 'PhabricatorRepositoryDaemon',
'PhabricatorRepositoryController' => 'PhabricatorController',
'PhabricatorRepositoryCreateController' => 'PhabricatorRepositoryController',
'PhabricatorRepositoryDAO' => 'PhabricatorLiskDAO',
'PhabricatorRepositoryDaemon' => 'PhabricatorDaemon',
'PhabricatorRepositoryDefaultCommitMessageDetailParser' => 'PhabricatorRepositoryCommitMessageDetailParser',
'PhabricatorRepositoryEditController' => 'PhabricatorRepositoryController',
'PhabricatorRepositoryGitCommitChangeParserWorker' => 'PhabricatorRepositoryCommitChangeParserWorker',
'PhabricatorRepositoryGitCommitDiscoveryDaemon' => 'PhabricatorRepositoryCommitDiscoveryDaemon',
'PhabricatorRepositoryGitCommitMessageParserWorker' => 'PhabricatorRepositoryCommitMessageParserWorker',
'PhabricatorRepositoryGitFetchDaemon' => 'PhabricatorRepositoryDaemon',
'PhabricatorRepositoryGitHubNotification' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositoryGitHubPostReceiveController' => 'PhabricatorRepositoryController',
'PhabricatorRepositoryListController' => 'PhabricatorRepositoryController',
'PhabricatorRepositoryShortcut' => 'PhabricatorRepositoryDAO',
'PhabricatorRepositorySvnCommitChangeParserWorker' => 'PhabricatorRepositoryCommitChangeParserWorker',
'PhabricatorRepositorySvnCommitDiscoveryDaemon' => 'PhabricatorRepositoryCommitDiscoveryDaemon',
'PhabricatorRepositorySvnCommitMessageParserWorker' => 'PhabricatorRepositoryCommitMessageParserWorker',
'PhabricatorSearchBaseController' => 'PhabricatorController',
'PhabricatorSearchController' => 'PhabricatorSearchBaseController',
'PhabricatorSearchDAO' => 'PhabricatorLiskDAO',
'PhabricatorSearchDifferentialIndexer' => 'PhabricatorSearchDocumentIndexer',
'PhabricatorSearchDocument' => 'PhabricatorSearchDAO',
'PhabricatorSearchDocumentField' => 'PhabricatorSearchDAO',
'PhabricatorSearchDocumentRelationship' => 'PhabricatorSearchDAO',
'PhabricatorSearchManiphestIndexer' => 'PhabricatorSearchDocumentIndexer',
'PhabricatorSearchMySQLExecutor' => 'PhabricatorSearchExecutor',
'PhabricatorSearchQuery' => 'PhabricatorSearchDAO',
'PhabricatorStandardPageView' => 'AphrontPageView',
'PhabricatorStatusController' => 'PhabricatorController',
'PhabricatorTaskmasterDaemon' => 'PhabricatorDaemon',
'PhabricatorTimelineCursor' => 'PhabricatorTimelineDAO',
'PhabricatorTimelineDAO' => 'PhabricatorLiskDAO',
'PhabricatorTimelineEvent' => 'PhabricatorTimelineDAO',
'PhabricatorTimelineEventData' => 'PhabricatorTimelineDAO',
'PhabricatorTypeaheadCommonDatasourceController' => 'PhabricatorTypeaheadDatasourceController',
'PhabricatorTypeaheadDatasourceController' => 'PhabricatorController',
'PhabricatorUIExampleController' => 'PhabricatorController',
'PhabricatorUIExampleRenderController' => 'PhabricatorUIExampleController',
'PhabricatorUIListFilterExample' => 'PhabricatorUIExample',
'PhabricatorUIPagerExample' => 'PhabricatorUIExample',
'PhabricatorUser' => 'PhabricatorUserDAO',
'PhabricatorUserDAO' => 'PhabricatorLiskDAO',
'PhabricatorUserOAuthInfo' => 'PhabricatorUserDAO',
'PhabricatorUserPreferences' => 'PhabricatorUserDAO',
'PhabricatorUserProfile' => 'PhabricatorUserDAO',
'PhabricatorUserSettingsController' => 'PhabricatorPeopleController',
'PhabricatorWorkerDAO' => 'PhabricatorLiskDAO',
'PhabricatorWorkerTask' => 'PhabricatorWorkerDAO',
'PhabricatorWorkerTaskData' => 'PhabricatorWorkerDAO',
'PhabricatorWorkerTaskDetailController' => 'PhabricatorDaemonController',
'PhabricatorXHPASTViewController' => 'PhabricatorController',
'PhabricatorXHPASTViewDAO' => 'PhabricatorLiskDAO',
'PhabricatorXHPASTViewFrameController' => 'PhabricatorXHPASTViewController',
'PhabricatorXHPASTViewFramesetController' => 'PhabricatorXHPASTViewController',
'PhabricatorXHPASTViewInputController' => 'PhabricatorXHPASTViewPanelController',
'PhabricatorXHPASTViewPanelController' => 'PhabricatorXHPASTViewController',
'PhabricatorXHPASTViewParseTree' => 'PhabricatorXHPASTViewDAO',
'PhabricatorXHPASTViewRunController' => 'PhabricatorXHPASTViewController',
'PhabricatorXHPASTViewStreamController' => 'PhabricatorXHPASTViewPanelController',
'PhabricatorXHPASTViewTreeController' => 'PhabricatorXHPASTViewPanelController',
'PhabricatorXHProfController' => 'PhabricatorController',
'PhabricatorXHProfProfileController' => 'PhabricatorXHProfController',
'PhabricatorXHProfProfileSymbolView' => 'AphrontView',
'PhabricatorXHProfProfileTopLevelView' => 'AphrontView',
),
'requires_interface' =>
array(
),
));
diff --git a/src/applications/differential/parser/markup/DifferentialMarkupEngineFactory.php b/src/applications/differential/parser/markup/DifferentialMarkupEngineFactory.php
index 1eefbb60a1..a65712a83a 100644
--- a/src/applications/differential/parser/markup/DifferentialMarkupEngineFactory.php
+++ b/src/applications/differential/parser/markup/DifferentialMarkupEngineFactory.php
@@ -1,56 +1,57 @@
<?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 DifferentialMarkupEngineFactory {
public function newDifferentialCommentMarkupEngine() {
$engine = new PhutilRemarkupEngine();
$engine->setConfig('preserve-linebreaks', true);
$rules = array();
$rules[] = new PhutilRemarkupRuleEscapeRemarkup();
$rules[] = new PhutilRemarkupRuleHyperlink();
$rules[] = new PhabricatorRemarkupRuleDifferential();
$rules[] = new PhabricatorRemarkupRuleDiffusion();
$rules[] = new PhabricatorRemarkupRuleManiphest();
+ $rules[] = new PhabricatorRemarkupRuleImageMacro();
$rules[] = new PhutilRemarkupRuleEscapeHTML();
$rules[] = new PhutilRemarkupRuleMonospace();
$rules[] = new PhutilRemarkupRuleBold();
$rules[] = new PhutilRemarkupRuleItalic();
$blocks = array();
$blocks[] = new PhutilRemarkupEngineRemarkupHeaderBlockRule();
$blocks[] = new PhutilRemarkupEngineRemarkupListBlockRule();
$blocks[] = new PhutilRemarkupEngineRemarkupCodeBlockRule();
$blocks[] = new PhutilRemarkupEngineRemarkupDefaultBlockRule();
foreach ($blocks as $block) {
if (!($block instanceof PhutilRemarkupEngineRemarkupCodeBlockRule)) {
$block->setMarkupRules($rules);
}
}
$engine->setBlockRules($blocks);
return $engine;
}
}
diff --git a/src/applications/differential/parser/markup/__init__.php b/src/applications/differential/parser/markup/__init__.php
index 7bc7a32d5a..4df4f32823 100644
--- a/src/applications/differential/parser/markup/__init__.php
+++ b/src/applications/differential/parser/markup/__init__.php
@@ -1,26 +1,27 @@
<?php
/**
* This file is automatically generated. Lint this module to rebuild it.
* @generated
*/
phutil_require_module('phabricator', 'infrastructure/markup/remarkup/markuprule/differential');
phutil_require_module('phabricator', 'infrastructure/markup/remarkup/markuprule/diffusion');
+phutil_require_module('phabricator', 'infrastructure/markup/remarkup/markuprule/imagemacro');
phutil_require_module('phabricator', 'infrastructure/markup/remarkup/markuprule/maniphest');
phutil_require_module('phutil', 'markup/engine/remarkup');
phutil_require_module('phutil', 'markup/engine/remarkup/blockrule/remarkupcode');
phutil_require_module('phutil', 'markup/engine/remarkup/blockrule/remarkupdefault');
phutil_require_module('phutil', 'markup/engine/remarkup/blockrule/remarkupheader');
phutil_require_module('phutil', 'markup/engine/remarkup/blockrule/remarkuplist');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/bold');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/escapehtml');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/escaperemarkup');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/hyperlink');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/italics');
phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/monospace');
phutil_require_source('DifferentialMarkupEngineFactory.php');
diff --git a/src/applications/files/storage/file/PhabricatorFile.php b/src/applications/files/storage/file/PhabricatorFile.php
index 4a900cdb0f..7ba0b05e23 100644
--- a/src/applications/files/storage/file/PhabricatorFile.php
+++ b/src/applications/files/storage/file/PhabricatorFile.php
@@ -1,191 +1,208 @@
<?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 PhabricatorFile extends PhabricatorFileDAO {
const STORAGE_ENGINE_BLOB = 'blob';
const STORAGE_FORMAT_RAW = 'raw';
// TODO: We need to reconcile this with MySQL packet size.
const FILE_SIZE_BYTE_LIMIT = 12582912;
protected $phid;
protected $name;
protected $mimeType;
protected $byteSize;
protected $storageEngine;
protected $storageFormat;
protected $storageHandle;
public function getConfiguration() {
return array(
self::CONFIG_AUX_PHID => true,
) + parent::getConfiguration();
}
public function generatePHID() {
return PhabricatorPHID::generateNewPHID(
PhabricatorPHIDConstants::PHID_TYPE_FILE);
}
public static function newFromPHPUpload($spec, array $params = array()) {
if (!$spec) {
throw new Exception("No file was uploaded!");
}
$err = idx($spec, 'error');
if ($err) {
throw new Exception("File upload failed with error '{$err}'.");
}
$tmp_name = idx($spec, 'tmp_name');
$is_valid = @is_uploaded_file($tmp_name);
if (!$is_valid) {
throw new Exception("File is not an uploaded file.");
}
$file_data = Filesystem::readFile($tmp_name);
$file_size = idx($spec, 'size');
if (strlen($file_data) != $file_size) {
throw new Exception("File size disagrees with uploaded size.");
}
$file_name = nonempty(
idx($params, 'name'),
idx($spec, 'name'));
$params = array(
'name' => $file_name,
) + $params;
return self::newFromFileData($file_data, $params);
}
public static function newFromFileData($data, array $params = array()) {
$file_size = strlen($data);
if ($file_size > self::FILE_SIZE_BYTE_LIMIT) {
throw new Exception("File is too large to store.");
}
$file_name = idx($params, 'name');
$file_name = self::normalizeFileName($file_name);
$file = new PhabricatorFile();
$file->setName($file_name);
$file->setByteSize(strlen($data));
$blob = new PhabricatorFileStorageBlob();
$blob->setData($data);
$blob->save();
// TODO: This stuff is almost certainly YAGNI, but we could imagine having
// an alternate disk store and gzipping or encrypting things or something
// crazy like that and this isn't toooo much extra code.
$file->setStorageEngine(self::STORAGE_ENGINE_BLOB);
$file->setStorageFormat(self::STORAGE_FORMAT_RAW);
$file->setStorageHandle($blob->getID());
if (isset($params['mime-type'])) {
$file->setMimeType($params['mime-type']);
} else {
try {
$tmp = new TempFile();
Filesystem::writeFile($tmp, $data);
list($stdout) = execx('file -b --mime %s', $tmp);
$file->setMimeType($stdout);
} catch (Exception $ex) {
// Be robust here since we don't really care that much about mime types.
}
}
$file->save();
return $file;
}
+ public static function newFromFileDownload($uri, $name) {
+ $uri = new PhutilURI($uri);
+ $timeout = stream_context_create(
+ array(
+ 'http' => array(
+ 'timeout' => 5,
+ ),
+ ));
+
+ $file_data = @file_get_contents($uri, false, $timeout);
+ if ($file_data === false) {
+ return null;
+ }
+
+ return self::newFromFileData($file_data, array('name' => $name));
+ }
+
public static function normalizeFileName($file_name) {
return preg_replace('/[^a-zA-Z0-9.~_-]/', '_', $file_name);
}
public function delete() {
$this->openTransaction();
switch ($this->getStorageEngine()) {
case self::STORAGE_ENGINE_BLOB:
$handle = $this->getStorageHandle();
$blob = id(new PhabricatorFileStorageBlob())->load($handle);
$blob->delete();
break;
default:
throw new Exception("Unknown storage engine!");
}
$ret = parent::delete();
$this->saveTransaction();
return $ret;
}
public function loadFileData() {
$handle = $this->getStorageHandle();
$data = null;
switch ($this->getStorageEngine()) {
case self::STORAGE_ENGINE_BLOB:
$blob = id(new PhabricatorFileStorageBlob())->load($handle);
if (!$blob) {
throw new Exception("Failed to load file blob data.");
}
$data = $blob->getData();
break;
default:
throw new Exception("Unknown storage engine.");
}
switch ($this->getStorageFormat()) {
case self::STORAGE_FORMAT_RAW:
$data = $data;
break;
default:
throw new Exception("Unknown storage format.");
}
return $data;
}
public function getViewURI() {
return PhabricatorFileURI::getViewURIForPHID($this->getPHID());
}
public function isViewableInBrowser() {
return ($this->getViewableMimeType() !== null);
}
public function getViewableMimeType() {
$mime_map = PhabricatorEnv::getEnvConfig('files.viewable-mime-types');
$mime_type = $this->getMimeType();
$mime_parts = explode(';', $mime_type);
$mime_type = trim(reset($mime_parts));
return idx($mime_map, $mime_type);
}
}
diff --git a/src/applications/files/storage/file/__init__.php b/src/applications/files/storage/file/__init__.php
index 1c82529ee4..c2533cf792 100644
--- a/src/applications/files/storage/file/__init__.php
+++ b/src/applications/files/storage/file/__init__.php
@@ -1,22 +1,23 @@
<?php
/**
* This file is automatically generated. Lint this module to rebuild it.
* @generated
*/
phutil_require_module('phabricator', 'applications/files/storage/base');
phutil_require_module('phabricator', 'applications/files/storage/storageblob');
phutil_require_module('phabricator', 'applications/files/uri');
phutil_require_module('phabricator', 'applications/phid/constants');
phutil_require_module('phabricator', 'applications/phid/storage/phid');
phutil_require_module('phabricator', 'infrastructure/env');
phutil_require_module('phutil', 'filesystem');
phutil_require_module('phutil', 'filesystem/tempfile');
phutil_require_module('phutil', 'future/exec');
+phutil_require_module('phutil', 'parser/uri');
phutil_require_module('phutil', 'utils');
phutil_require_source('PhabricatorFile.php');
diff --git a/src/applications/files/storage/imagemacro/PhabricatorFileImageMacro.php b/src/applications/files/storage/imagemacro/PhabricatorFileImageMacro.php
new file mode 100644
index 0000000000..85825151e2
--- /dev/null
+++ b/src/applications/files/storage/imagemacro/PhabricatorFileImageMacro.php
@@ -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 PhabricatorFileImageMacro extends PhabricatorFileDAO {
+
+ protected $filePHID;
+ protected $name;
+
+ public function getConfiguration() {
+ return array(
+ self::CONFIG_TIMESTAMPS => false,
+ ) + parent::getConfiguration();
+ }
+
+ static public function newFromImageURI($uri, $file_name, $image_macro_name) {
+ $file = PhabricatorFile::newFromFileDownload($uri, $file_name);
+
+ if (!$file) {
+ return null;
+ }
+
+ $image_macro = new PhabricatorFileImageMacro();
+ $image_macro->setName($image_macro_name);
+ $image_macro->setFilePHID($file->getPHID());
+ $image_macro->save();
+
+ return $image_macro;
+ }
+}
+
diff --git a/src/applications/files/storage/imagemacro/__init__.php b/src/applications/files/storage/imagemacro/__init__.php
new file mode 100644
index 0000000000..613481dc3c
--- /dev/null
+++ b/src/applications/files/storage/imagemacro/__init__.php
@@ -0,0 +1,13 @@
+<?php
+/**
+ * This file is automatically generated. Lint this module to rebuild it.
+ * @generated
+ */
+
+
+
+phutil_require_module('phabricator', 'applications/files/storage/base');
+phutil_require_module('phabricator', 'applications/files/storage/file');
+
+
+phutil_require_source('PhabricatorFileImageMacro.php');
diff --git a/src/infrastructure/markup/remarkup/markuprule/imagemacro/PhabricatorRemarkupRuleImageMacro.php b/src/infrastructure/markup/remarkup/markuprule/imagemacro/PhabricatorRemarkupRuleImageMacro.php
new file mode 100644
index 0000000000..13a887fe44
--- /dev/null
+++ b/src/infrastructure/markup/remarkup/markuprule/imagemacro/PhabricatorRemarkupRuleImageMacro.php
@@ -0,0 +1,87 @@
+<?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.
+ */
+
+/**
+ * @group markup
+ */
+class PhabricatorRemarkupRuleImageMacro
+ extends PhutilRemarkupRule {
+
+ const RANDOM_IMAGE_NAME = 'randomon';
+ private $images = array();
+ private $hash = 0;
+
+ public function __construct() {
+ $rows = id(new PhabricatorFileImageMacro())->loadAll();
+ foreach ($rows as $row) {
+ $this->images[$row->getName()] = $row->getFilePHID();
+ }
+ $this->images[self::RANDOM_IMAGE_NAME] = '';
+ }
+
+ public function apply($text) {
+ $this->hash = 0;
+
+ return preg_replace_callback(
+ '@\b([a-zA-Z0-9_\-]+)\b@U',
+ array($this, 'markupImageMacro'),
+ $text);
+ }
+
+ /**
+ * Silly function for generating some 'randomness' based on the
+ * words in the text
+ */
+ private function updateHash($word) {
+ // Simple Jenkins hash
+ for ($ii = 0; $ii < strlen($word); $ii++) {
+ $this->hash += ord($word[$ii]);
+ $this->hash += ($this->hash << 10);
+ $this->hash ^= ($this->hash >> 6);
+ }
+ }
+
+ public function markupImageMacro($matches) {
+ // Update the hash that is used for defining each 'randomon' image. This way
+ // each 'randomon' image will be different, but they won't change when the
+ // text is updated.
+ $this->updateHash($matches[1]);
+
+ if (array_key_exists($matches[1], $this->images)) {
+ if ($matches[1] === self::RANDOM_IMAGE_NAME) {
+ $keys = array_keys($this->images);
+ $phid = $this->images[$keys[$this->hash % count($this->images)]];
+ } else {
+ $phid = $this->images[$matches[1]];
+ }
+
+
+ $img = phutil_render_tag(
+ 'img',
+ array(
+ 'src' => PhabricatorFileURI::getViewURIForPHID($phid),
+ 'alt' => $matches[1],
+ 'title' => $matches[1]),
+ null);
+ return $this->getEngine()->storeText($img);
+ } else {
+ return $matches[1];
+ }
+ }
+
+}
diff --git a/src/infrastructure/markup/remarkup/markuprule/imagemacro/__init__.php b/src/infrastructure/markup/remarkup/markuprule/imagemacro/__init__.php
new file mode 100644
index 0000000000..d742a178a2
--- /dev/null
+++ b/src/infrastructure/markup/remarkup/markuprule/imagemacro/__init__.php
@@ -0,0 +1,17 @@
+<?php
+/**
+ * This file is automatically generated. Lint this module to rebuild it.
+ * @generated
+ */
+
+
+
+phutil_require_module('phabricator', 'applications/files/storage/imagemacro');
+phutil_require_module('phabricator', 'applications/files/uri');
+
+phutil_require_module('phutil', 'markup');
+phutil_require_module('phutil', 'markup/engine/remarkup/markuprule/base');
+phutil_require_module('phutil', 'utils');
+
+
+phutil_require_source('PhabricatorRemarkupRuleImageMacro.php');

File Metadata

Mime Type
text/x-diff
Expires
Mon, Dec 1, 5:32 AM (1 d, 6 h)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
430242
Default Alt Text
(74 KB)

Event Timeline