jenkins-bot has submitted this change and it was merged.

Change subject: Autolink typed ISBN/RFC/PMIDs
......................................................................


Autolink typed ISBN/RFC/PMIDs

Depends on Ibdad2fa98fca08eeaa96bf33a08dd7723c1edb8c in Parsoid.

Depends on I3dcd289ed7b565b9162ee671038eeb45449e1215 in ve-core.

Bug: T109498
Change-Id: I5650410d7fca30c90baddd4f0c3f6d80e6b39042
---
M modules/ve-mw/tests/ui/actions/ve.ui.MWLinkAction.test.js
M modules/ve-mw/ui/actions/ve.ui.MWLinkAction.js
2 files changed, 139 insertions(+), 14 deletions(-)

Approvals:
  Jforrester: Looks good to me, but someone else must approve
  Esanders: Looks good to me, approved
  jenkins-bot: Verified



diff --git a/modules/ve-mw/tests/ui/actions/ve.ui.MWLinkAction.test.js 
b/modules/ve-mw/tests/ui/actions/ve.ui.MWLinkAction.test.js
index eea42bd..ba60cc3 100644
--- a/modules/ve-mw/tests/ui/actions/ve.ui.MWLinkAction.test.js
+++ b/modules/ve-mw/tests/ui/actions/ve.ui.MWLinkAction.test.js
@@ -10,14 +10,17 @@
 /* Tests */
 
 function runMWAutolinkTest( assert, html, method, range, expectedRange, 
expectedData, expectedOriginalData, msg ) {
-       var status,
+       var status, actualData,
                expectFail = /^Don't/.test( msg ),
                surface = ve.test.utils.createModelOnlySurfaceFromHtml( html || 
ve.dm.example.html ),
                linkAction = new ve.ui.MWLinkAction( surface ),
                data = ve.copy( surface.getModel().getDocument().getFullData() 
),
-               originalData = ve.copy( data );
+               originalData = ve.copy( data ),
+               makeLinkAnnotation = function ( linktext ) {
+                       return linkAction.getLinkAnnotation( linktext ).element;
+               };
 
-       expectedData( data );
+       expectedData( data, makeLinkAnnotation );
        if ( expectedOriginalData ) {
                expectedOriginalData( originalData );
        }
@@ -25,7 +28,9 @@
        status = linkAction[ method ]();
        assert.equal( status, !expectFail, msg + ': action return value' );
 
-       assert.equalLinearData( surface.getModel().getDocument().getFullData(), 
data, msg + ': data models match' );
+       actualData = surface.getModel().getDocument().getFullData();
+       ve.dm.example.postprocessAnnotations( actualData, 
surface.getModel().getDocument().getStore() );
+       assert.equalLinearData( actualData, data, msg + ': data models match' );
        assert.equalRange( surface.getModel().getSelection().getRange(), 
expectedRange, msg + ': ranges match' );
 
        if ( status ) {
@@ -40,17 +45,90 @@
        var i,
                cases = [
                        {
+                               msg: 'Strip trailing punctuation (but not 
matched parens)',
                                html: 
'<p>https://en.wikipedia.org/wiki/Red_(disambiguation) xyz</p>',
                                range: new ve.Range( 1, 52 ),
                                method: 'autolinkUrl',
                                expectedRange: new ve.Range( 52, 52 ),
-                               expectedData: function ( data ) {
-                                       var i;
+                               expectedData: function ( data, makeAnnotation ) 
{
+                                       var i,
+                                               a = makeAnnotation( 
'https://en.wikipedia.org/wiki/Red_(disambiguation)' );
                                        for ( i = 1; i < 51; i++ ) {
-                                               data[ i ] = [ data[ i ], [ 0 ] 
];
+                                               data[ i ] = [ data[ i ], [ a ] 
];
                                        }
-                               },
-                               msg: 'Strip trailing punctuation (but not 
matched parens)'
+                               }
+                       },
+                       {
+                               msg: 'Autolink valid RFC',
+                               html: '<p>RFC 1234 xyz</p>',
+                               range: new ve.Range( 1, 10 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 10, 10 ),
+                               expectedData: function ( data, makeAnnotation ) 
{
+                                       var i,
+                                               a = makeAnnotation( 
'//tools.ietf.org/html/rfc1234' );
+                                       for ( i = 1; i < 9; i++ ) {
+                                               data[ i ] = [ data[ i ], [ a ] 
];
+                                       }
+                               }
+                       },
+                       {
+                               msg: 'Don\'t autolink invalid RFC',
+                               html: '<p>RFC 123x xyz</p>',
+                               range: new ve.Range( 1, 10 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 1, 10 ),
+                               expectedData: function ( /*data, 
makeAnnotation*/ ) {
+                                       /* no change, no link */
+                               }
+                       },
+                       {
+                               msg: 'Autolink valid PMID',
+                               html: '<p>PMID 1234 xyz</p>',
+                               range: new ve.Range( 1, 11 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 11, 11 ),
+                               expectedData: function ( data, makeAnnotation ) 
{
+                                       var i,
+                                               a = makeAnnotation( 
'//www.ncbi.nlm.nih.gov/pubmed/1234?dopt=Abstract' );
+                                       for ( i = 1; i < 10; i++ ) {
+                                               data[ i ] = [ data[ i ], [ a ] 
];
+                                       }
+                               }
+                       },
+                       {
+                               msg: 'Don\'t autolink invalid PMID',
+                               html: '<p>PMID 123x xyz</p>',
+                               range: new ve.Range( 1, 11 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 1, 11 ),
+                               expectedData: function ( /*data, 
makeAnnotation*/ ) {
+                                       /* no change, no link */
+                               }
+                       },
+                       {
+                               msg: 'Autolink valid ISBN',
+                               html: '<p>ISBN 978-0596517748 xyz</p>',
+                               range: new ve.Range( 1, 21 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 21, 21 ),
+                               expectedData: function ( data, makeAnnotation ) 
{
+                                       var i,
+                                               a = makeAnnotation( 
'./Special:BookSources/9780596517748' );
+                                       for ( i = 1; i < 20; i++ ) {
+                                               data[ i ] = [ data[ i ], [ a ] 
];
+                                       }
+                               }
+                       },
+                       {
+                               msg: 'Don\'t autolink invalid ISBN',
+                               html: '<p>ISBN 978-059651774 xyz</p>',
+                               range: new ve.Range( 1, 20 ),
+                               method: 'autolinkMagicLink',
+                               expectedRange: new ve.Range( 1, 20 ),
+                               expectedData: function ( /*data, 
makeAnnotation*/ ) {
+                                       /* no change, no link */
+                               }
                        }
                ];
 
diff --git a/modules/ve-mw/ui/actions/ve.ui.MWLinkAction.js 
b/modules/ve-mw/ui/actions/ve.ui.MWLinkAction.js
index 5bf915f..62acfa8 100644
--- a/modules/ve-mw/ui/actions/ve.ui.MWLinkAction.js
+++ b/modules/ve-mw/ui/actions/ve.ui.MWLinkAction.js
@@ -31,7 +31,7 @@
  * @static
  * @property
  */
-ve.ui.MWLinkAction.static.methods = 
ve.ui.MWLinkAction.super.static.methods.concat( [ 'open' ] );
+ve.ui.MWLinkAction.static.methods = 
ve.ui.MWLinkAction.super.static.methods.concat( [ 'open', 'autolinkMagicLink' ] 
);
 
 /* Methods */
 
@@ -53,14 +53,27 @@
  * @inheritdoc
  * @return {ve.dm.MWExternalLinkAnnotation} The annotation to use.
  */
-ve.ui.MWLinkAction.prototype.getLinkAnnotation = function ( href ) {
-       var title,
+ve.ui.MWLinkAction.prototype.getLinkAnnotation = function ( linktext ) {
+       var title, targetData, m,
+               href = linktext;
+       // The link has been validated in #autolinkMagicLink and/or
+       // #autolinkUrl, so we can use a quick and dirty regexp here to pull
+       // apart the magic link.
+       m = /^(RFC|PMID|ISBN)\s+(\S.*)$/.exec( linktext );
+       if ( m && m[ 1 ] === 'RFC' ) {
+               href = '//tools.ietf.org/html/rfc' + m[ 2 ];
+       } else if ( m && m[ 1 ] === 'PMID' ) {
+               href = '//www.ncbi.nlm.nih.gov/pubmed/' + m[ 2 ] + 
'?dopt=Abstract';
+       } else if ( m && m[ 1 ] === 'ISBN' ) {
+               title = mw.Title.newFromText( 'Special:BookSources/' + m[ 2 
].replace( /[^0-9Xx]/g, '' ) );
+       } else {
                targetData = 
ve.dm.MWInternalLinkAnnotation.static.getTargetDataFromHref(
                        href,
                        this.surface.getModel().getDocument().getHtmlDocument()
                );
-       if ( targetData.isInternal ) {
-               title = mw.Title.newFromText( targetData.title );
+               if ( targetData.isInternal ) {
+                       title = mw.Title.newFromText( targetData.title );
+               }
        }
        return title ?
                ve.dm.MWInternalLinkAnnotation.static.newFromTitle( title ) :
@@ -68,6 +81,27 @@
                        type: 'link/mwExternal',
                        attributes: { href: href }
                } );
+};
+
+/**
+ * Autolink the selected RFC/PMID/ISBN, which may have trailing whitespace.
+ *
+ * @see ve.ui.LinkAction#autolinkUrl
+ * @method
+ * @return {boolean}
+ *   True if the selection is a valid RFC/PMID/ISBN and the autolink action
+ *   was executed; otherwise false.
+ */
+ve.ui.MWLinkAction.prototype.autolinkMagicLink = function () {
+       return this.autolink( function ( linktext ) {
+               if ( /^(RFC|PMID) [0-9]+$/.test( linktext ) ) {
+                       return true; // Valid RFC/PMID
+               }
+               if ( /^ISBN (97[89][- ]?)?([0-9][- ]?){9}[0-9Xx]$/.test( 
linktext ) ) {
+                       return true; // Valid ISBN
+               }
+               return false;
+       } );
 };
 
 /**
@@ -90,3 +124,16 @@
 /* Registration */
 
 ve.ui.actionFactory.register( ve.ui.MWLinkAction );
+
+ve.ui.commandRegistry.register(
+       new ve.ui.Command(
+               'autolinkMagicLink', ve.ui.MWLinkAction.static.name, 
'autolinkMagicLink',
+               { supportedSelections: [ 'linear' ] }
+       )
+);
+
+ve.ui.sequenceRegistry.register(
+       // This regexp doesn't have to be precise; we'll validate the magic
+       // link in #autolinkMagicLink above.
+       new ve.ui.Sequence( 'autolinkMagicLink', 'autolinkMagicLink', 
/\b(RFC|PMID|ISBN)\s+[0-9]([- 0-9]*[0-9Xx])?(\s|\n\n)$/, 0, true )
+);

-- 
To view, visit https://gerrit.wikimedia.org/r/232391
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings

Gerrit-MessageType: merged
Gerrit-Change-Id: I5650410d7fca30c90baddd4f0c3f6d80e6b39042
Gerrit-PatchSet: 5
Gerrit-Project: mediawiki/extensions/VisualEditor
Gerrit-Branch: master
Gerrit-Owner: Cscott <[email protected]>
Gerrit-Reviewer: Cscott <[email protected]>
Gerrit-Reviewer: Esanders <[email protected]>
Gerrit-Reviewer: Jforrester <[email protected]>
Gerrit-Reviewer: jenkins-bot <>

_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits

Reply via email to