book-source 0.3.10 → 0.3.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/lib/StructuredDocument.js +174 -37
- package/lib/documentParts.js +24 -3
- package/lib/postProcesses.js +150 -0
- package/package.json +1 -1
- package/.eslintrc.js +0 -168
- package/Makefile +0 -112
- package/documentation.md +0 -17
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
The MIT License (MIT)
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2014 Cédric Ronvel
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -30,7 +30,6 @@
|
|
|
30
30
|
|
|
31
31
|
const documentParts = require( './documentParts.js' ) ;
|
|
32
32
|
const Style = require( './Style.js' ) ;
|
|
33
|
-
const Theme = require( './Theme.js' ) ;
|
|
34
33
|
const textPostFilters = require( './textPostFilters.js' ) ;
|
|
35
34
|
|
|
36
35
|
const inPlaceFilter = require( 'array-kit/lib/inPlaceFilter.js' ) ;
|
|
@@ -38,24 +37,41 @@ const inPlaceFilter = require( 'array-kit/lib/inPlaceFilter.js' ) ;
|
|
|
38
37
|
|
|
39
38
|
|
|
40
39
|
function StructuredDocument() {
|
|
40
|
+
this.type = 'document' ;
|
|
41
41
|
this.title = 'Document' ;
|
|
42
42
|
this.metadata = null ;
|
|
43
43
|
this.theme = null ;
|
|
44
|
+
this.summary = null ;
|
|
44
45
|
this.parts = [] ;
|
|
46
|
+
//this.idList = new Set() ;
|
|
45
47
|
}
|
|
46
48
|
|
|
47
49
|
module.exports = StructuredDocument ;
|
|
48
50
|
|
|
51
|
+
// Circular require, should come after exporting
|
|
52
|
+
const postProcesses = require( './postProcesses.js' ) ;
|
|
49
53
|
|
|
50
54
|
|
|
51
|
-
StructuredDocument.prototype.render = function( renderer ) {
|
|
52
|
-
var meta = {
|
|
53
|
-
title: this.title
|
|
54
|
-
} ;
|
|
55
55
|
|
|
56
|
-
|
|
56
|
+
StructuredDocument.prototype.render = function( renderer , special = null ) {
|
|
57
|
+
let toRender ;
|
|
58
|
+
|
|
59
|
+
switch ( special ) {
|
|
60
|
+
case 'summary' :
|
|
61
|
+
toRender = this.summary ? [ this.summary ] : [] ;
|
|
62
|
+
break ;
|
|
63
|
+
default :
|
|
64
|
+
toRender = this.parts ;
|
|
65
|
+
break ;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
let output = this.renderParts( renderer , toRender , [] , [ {} ] ) ;
|
|
57
69
|
|
|
58
70
|
if ( renderer.document ) {
|
|
71
|
+
let meta = {
|
|
72
|
+
title: this.title
|
|
73
|
+
} ;
|
|
74
|
+
|
|
59
75
|
output = renderer.document( meta , output ) ;
|
|
60
76
|
}
|
|
61
77
|
|
|
@@ -199,25 +215,79 @@ StructuredDocument.prototype.autoTitle = function() {
|
|
|
199
215
|
|
|
200
216
|
if ( ! header ) { return ; }
|
|
201
217
|
|
|
202
|
-
str = StructuredDocument.getText( header
|
|
218
|
+
str = StructuredDocument.getText( header ) ;
|
|
203
219
|
if ( str ) { this.title = str ; }
|
|
204
220
|
} ;
|
|
205
221
|
|
|
206
222
|
|
|
207
223
|
|
|
208
|
-
StructuredDocument.
|
|
209
|
-
var
|
|
224
|
+
StructuredDocument.prototype.postProcess = function( params = {} ) {
|
|
225
|
+
var data = {} ,
|
|
226
|
+
postProcessArray = [] ,
|
|
227
|
+
postProcessMap = new Map() ;
|
|
210
228
|
|
|
211
|
-
for ( let
|
|
212
|
-
if (
|
|
213
|
-
|
|
229
|
+
for ( let postProcessName of Object.keys( params ) ) {
|
|
230
|
+
if ( ! postProcesses[ postProcessName ] || ! params[ postProcessName ] ) { continue ; }
|
|
231
|
+
|
|
232
|
+
let postProcess = postProcesses[ postProcessName ] ;
|
|
233
|
+
|
|
234
|
+
// Add required post-process first
|
|
235
|
+
if ( postProcess.require ) {
|
|
236
|
+
for ( let requiredName of postProcess.require ) {
|
|
237
|
+
if ( ! postProcessMap.has( requiredName ) ) {
|
|
238
|
+
let entry = { name: requiredName , params: {} } ;
|
|
239
|
+
postProcessArray.push( entry ) ;
|
|
240
|
+
postProcessMap.set( requiredName , entry ) ;
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
if ( postProcessMap.has( postProcessName ) ) {
|
|
246
|
+
// It was already added by a dependency, just patch the params if needed
|
|
247
|
+
if ( typeof params[ postProcessName ] === 'object' ) {
|
|
248
|
+
let entry = postProcessMap.get( postProcessName ) ;
|
|
249
|
+
entry.params = Object.assign( {} , params[ postProcessName ] ) ;
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
else {
|
|
253
|
+
let entry = {
|
|
254
|
+
name: postProcessName ,
|
|
255
|
+
params: typeof params[ postProcessName ] === 'object' ? Object.assign( {} , params[ postProcessName ] ) : {}
|
|
256
|
+
} ;
|
|
257
|
+
|
|
258
|
+
postProcessArray.push( entry ) ;
|
|
259
|
+
postProcessMap.set( postProcessName , entry ) ;
|
|
260
|
+
}
|
|
214
261
|
}
|
|
215
262
|
|
|
216
|
-
|
|
263
|
+
for ( let entry of postProcessArray ) {
|
|
264
|
+
if ( postProcesses[ entry.name ].init ) {
|
|
265
|
+
postProcesses[ entry.name ].init( this , entry.params , data ) ;
|
|
266
|
+
}
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
this.postProcessRecursive( this , postProcessArray , data ) ;
|
|
270
|
+
|
|
271
|
+
for ( let entry of postProcessArray ) {
|
|
272
|
+
if ( postProcesses[ entry.name ].finalize ) {
|
|
273
|
+
postProcesses[ entry.name ].finalize( this , entry.params , data ) ;
|
|
274
|
+
}
|
|
275
|
+
}
|
|
217
276
|
} ;
|
|
218
277
|
|
|
219
|
-
|
|
220
|
-
|
|
278
|
+
|
|
279
|
+
|
|
280
|
+
StructuredDocument.prototype.postProcessRecursive = function( object , postProcessArray , data ) {
|
|
281
|
+
for ( let entry of postProcessArray ) {
|
|
282
|
+
postProcesses[ entry.name ]( this , object , entry.params , data ) ;
|
|
283
|
+
}
|
|
284
|
+
|
|
285
|
+
if ( object.parts && object.parts.length ) {
|
|
286
|
+
for ( let part of object.parts ) {
|
|
287
|
+
this.postProcessRecursive( part , postProcessArray , data ) ;
|
|
288
|
+
}
|
|
289
|
+
}
|
|
290
|
+
} ;
|
|
221
291
|
|
|
222
292
|
|
|
223
293
|
|
|
@@ -251,10 +321,49 @@ StructuredDocument.prototype.oneTextPostFilter = function( postFilter , parts ,
|
|
|
251
321
|
|
|
252
322
|
|
|
253
323
|
|
|
324
|
+
// Utility methods
|
|
325
|
+
|
|
326
|
+
|
|
327
|
+
|
|
328
|
+
StructuredDocument.getText = function( object ) {
|
|
329
|
+
if ( Array.isArray( object ) ) {
|
|
330
|
+
object = { parts: object } ;
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
if ( object.text ) { return object.text ; }
|
|
334
|
+
if ( ! object.parts || ! object.parts.length ) { return '' ; }
|
|
335
|
+
|
|
336
|
+
let str = '' ;
|
|
337
|
+
|
|
338
|
+
for ( let part of object.parts ) {
|
|
339
|
+
str += StructuredDocument.getText( part ) ;
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
return str ;
|
|
343
|
+
} ;
|
|
344
|
+
|
|
345
|
+
// Backward compatibility/API
|
|
346
|
+
StructuredDocument.prototype.getText = function( object = this ) { return StructuredDocument.getText( object ) ; } ;
|
|
347
|
+
|
|
348
|
+
|
|
349
|
+
|
|
350
|
+
StructuredDocument.textToId = function( text ) {
|
|
351
|
+
return text
|
|
352
|
+
.trim()
|
|
353
|
+
.normalize( 'NFC' )
|
|
354
|
+
.replace( /[\s]+/g , '_' )
|
|
355
|
+
.replace( /[^\p{L}\p{N}_.:-]/gu , '' )
|
|
356
|
+
.replace( /_+/g , '_' ) ;
|
|
357
|
+
} ;
|
|
358
|
+
|
|
359
|
+
|
|
360
|
+
|
|
254
361
|
// Parser
|
|
255
362
|
|
|
256
|
-
|
|
257
|
-
|
|
363
|
+
|
|
364
|
+
|
|
365
|
+
StructuredDocument.parse = function( str , params ) {
|
|
366
|
+
if ( ! params || typeof params !== 'object' ) { params = {} ; }
|
|
258
367
|
|
|
259
368
|
if ( typeof str !== 'string' ) {
|
|
260
369
|
if ( str && typeof str === 'object' ) { str = str.toString() ; }
|
|
@@ -281,10 +390,11 @@ StructuredDocument.parse = function( str , options ) {
|
|
|
281
390
|
parseBlocks( str , ctx ) ;
|
|
282
391
|
|
|
283
392
|
for ( let table of ctx.rowSpanTables ) { postProcessTableRowSpan( table ) ; }
|
|
393
|
+
|
|
284
394
|
ctx.structuredDocument.autoTitle() ;
|
|
285
395
|
|
|
286
396
|
if ( ctx.rawMetadata ) {
|
|
287
|
-
let metadataParser =
|
|
397
|
+
let metadataParser = params.metadataParser || JSON.parse ;
|
|
288
398
|
for ( let type in ctx.rawMetadata ) {
|
|
289
399
|
try {
|
|
290
400
|
let parsed = metadataParser( ctx.rawMetadata[ type ] ) ;
|
|
@@ -299,10 +409,6 @@ StructuredDocument.parse = function( str , options ) {
|
|
|
299
409
|
}
|
|
300
410
|
}
|
|
301
411
|
|
|
302
|
-
// Call depthManagement() one last time, because some instanceOf may still be hanging...
|
|
303
|
-
//ctx.depth = -1 ;
|
|
304
|
-
//depthManagement( ctx ) ;
|
|
305
|
-
|
|
306
412
|
return ctx.structuredDocument ;
|
|
307
413
|
} ;
|
|
308
414
|
|
|
@@ -391,6 +497,9 @@ function parseBlock( str , ctx ) {
|
|
|
391
497
|
case BLOCK_METADATA :
|
|
392
498
|
parseMetadata( str , ctx ) ;
|
|
393
499
|
break ;
|
|
500
|
+
case BLOCK_SPECIAL :
|
|
501
|
+
parseSpecial( str , ctx ) ;
|
|
502
|
+
break ;
|
|
394
503
|
default :
|
|
395
504
|
throw new Error( "Bad block detection: " + blockType ) ;
|
|
396
505
|
}
|
|
@@ -499,6 +608,7 @@ const BLOCK_TABLE_ROW_THICK_SEPARATOR = 42 ;
|
|
|
499
608
|
const BLOCK_TABLE_CAPTION = 43 ;
|
|
500
609
|
const BLOCK_ANCHOR = 50 ;
|
|
501
610
|
const BLOCK_METADATA = 60 ;
|
|
611
|
+
const BLOCK_SPECIAL = 80 ;
|
|
502
612
|
|
|
503
613
|
function detectBlockType( str , i ) {
|
|
504
614
|
if ( str[ i ] === '\\' ) {
|
|
@@ -506,14 +616,17 @@ function detectBlockType( str , i ) {
|
|
|
506
616
|
}
|
|
507
617
|
|
|
508
618
|
if ( str[ i ] === '#' ) {
|
|
509
|
-
if ( str[ i + 1 ] === '(' ) {
|
|
619
|
+
if ( str[ i + 1 ] === '(' ) {
|
|
620
|
+
if ( str[ i + 2 ] === '%' ) { return BLOCK_SPECIAL ; }
|
|
621
|
+
return BLOCK_ANCHOR ;
|
|
622
|
+
}
|
|
510
623
|
return BLOCK_HEADER ;
|
|
511
624
|
}
|
|
512
625
|
|
|
513
626
|
if ( str[ i ] === '!' && str[ i + 2 ] === '[' ) {
|
|
514
627
|
if ( str[ i + 1 ] === '=' ) { return BLOCK_MEDIA ; }
|
|
515
|
-
|
|
516
|
-
|
|
628
|
+
if ( str[ i + 1 ] === '<' ) { return BLOCK_FLOAT_LEFT_MEDIA ; }
|
|
629
|
+
if ( str[ i + 1 ] === '>' ) { return BLOCK_FLOAT_RIGHT_MEDIA ; }
|
|
517
630
|
return BLOCK_PARAGRAPH ;
|
|
518
631
|
}
|
|
519
632
|
|
|
@@ -864,6 +977,18 @@ function parseAnchor( str , ctx ) {
|
|
|
864
977
|
|
|
865
978
|
|
|
866
979
|
|
|
980
|
+
function parseSpecial( str , ctx ) {
|
|
981
|
+
//console.log( "parseSpecial()" ) ;
|
|
982
|
+
var end = searchCloser( str , ctx.i + 3 , '(' , ')' , true ) ;
|
|
983
|
+
if ( end < 0 ) { return parseParagraph( str , ctx ) ; }
|
|
984
|
+
|
|
985
|
+
ctx.parts.push( new documentParts.Special( str.slice( ctx.i + 3 , end ) ) ) ;
|
|
986
|
+
|
|
987
|
+
ctx.i = end + 1 ;
|
|
988
|
+
}
|
|
989
|
+
|
|
990
|
+
|
|
991
|
+
|
|
867
992
|
function parseTableCaption( str , ctx ) {
|
|
868
993
|
//console.log( "parseTableCaption()" ) ;
|
|
869
994
|
var lastCharOfLine = searchLastCharOfLine( str , ctx.i + 1 ) ;
|
|
@@ -901,7 +1026,7 @@ function parseTableCaption( str , ctx ) {
|
|
|
901
1026
|
if ( data?.style?.[ 0 ] ) { tableCaption.style = data.style[ 0 ] ; }
|
|
902
1027
|
}
|
|
903
1028
|
|
|
904
|
-
ctx.i = lastCharOfLine + 1 ;
|
|
1029
|
+
ctx.i = searchEndOfLine( str , lastCharOfLine !== - 1 ? lastCharOfLine : ctx.i ) + 1 ;
|
|
905
1030
|
}
|
|
906
1031
|
|
|
907
1032
|
|
|
@@ -991,7 +1116,7 @@ function parseTableRow( str , ctx ) {
|
|
|
991
1116
|
currentBar = columnSeparator ? nextBar + 1 : nextBar ;
|
|
992
1117
|
}
|
|
993
1118
|
|
|
994
|
-
// Compute cells indexes, columnSpan,
|
|
1119
|
+
// Compute cells indexes, columnSpan, column template, and add missing cells
|
|
995
1120
|
computeIndexColumnSpan( ctx , table , tableRow ) ;
|
|
996
1121
|
|
|
997
1122
|
if ( str[ currentBar + 1 ] === '<' ) {
|
|
@@ -1000,7 +1125,7 @@ function parseTableRow( str , ctx ) {
|
|
|
1000
1125
|
if ( data?.style?.[ 0 ] ) { tableRow.style = data.style[ 0 ] ; }
|
|
1001
1126
|
}
|
|
1002
1127
|
|
|
1003
|
-
ctx.i = lastCharOfLine + 1 ;
|
|
1128
|
+
ctx.i = searchEndOfLine( str , lastCharOfLine !== - 1 ? lastCharOfLine : ctx.i ) + 1 ;
|
|
1004
1129
|
}
|
|
1005
1130
|
|
|
1006
1131
|
|
|
@@ -1033,7 +1158,7 @@ function parseTableMultilineRow( str , ctx , lastCharOfLine , table , tableRow )
|
|
|
1033
1158
|
columnIndex ++ ;
|
|
1034
1159
|
}
|
|
1035
1160
|
|
|
1036
|
-
ctx.i = lastCharOfLine + 1 ;
|
|
1161
|
+
ctx.i = searchEndOfLine( str , lastCharOfLine !== - 1 ? lastCharOfLine : ctx.i ) + 1 ;
|
|
1037
1162
|
}
|
|
1038
1163
|
|
|
1039
1164
|
|
|
@@ -1143,7 +1268,7 @@ function parseTableRowSeparator( str , ctx , thick = false ) {
|
|
|
1143
1268
|
separatorCellIndex ++ ;
|
|
1144
1269
|
}
|
|
1145
1270
|
|
|
1146
|
-
ctx.i = lastCharOfLine + 1 ;
|
|
1271
|
+
ctx.i = searchEndOfLine( str , lastCharOfLine !== - 1 ? lastCharOfLine : ctx.i ) + 1 ;
|
|
1147
1272
|
}
|
|
1148
1273
|
|
|
1149
1274
|
|
|
@@ -1291,15 +1416,16 @@ function parseTableHeadRowSeparator( str , ctx , thick , lastCharOfLine ) {
|
|
|
1291
1416
|
}
|
|
1292
1417
|
|
|
1293
1418
|
if ( tableHeadRow ) {
|
|
1294
|
-
// Compute cells indexes, columnSpan,
|
|
1419
|
+
// Compute cells indexes, columnSpan, column template, and add missing cells
|
|
1295
1420
|
computeIndexColumnSpan( ctx , table , tableHeadRow ) ;
|
|
1296
1421
|
}
|
|
1297
1422
|
|
|
1298
|
-
ctx.i = lastCharOfLine + 1 ;
|
|
1423
|
+
ctx.i = searchEndOfLine( str , lastCharOfLine !== - 1 ? lastCharOfLine : ctx.i ) + 1 ;
|
|
1299
1424
|
}
|
|
1300
1425
|
|
|
1301
1426
|
|
|
1302
1427
|
|
|
1428
|
+
// Compute cells indexes, columnSpan, column template, and add missing cells
|
|
1303
1429
|
function computeIndexColumnSpan( ctx , table , tableRow ) {
|
|
1304
1430
|
var tableCell , cellIndex , column , columnIndex , columnSpan ,
|
|
1305
1431
|
columns = table.columns ,
|
|
@@ -1336,6 +1462,19 @@ function computeIndexColumnSpan( ctx , table , tableRow ) {
|
|
|
1336
1462
|
}
|
|
1337
1463
|
}
|
|
1338
1464
|
}
|
|
1465
|
+
|
|
1466
|
+
// Add missing cells
|
|
1467
|
+
if ( columns ) {
|
|
1468
|
+
for ( ; extraSpan > 0 ; extraSpan -- ) {
|
|
1469
|
+
columnIndex = table.columns.length - extraSpan ;
|
|
1470
|
+
column = table.columns[ columnIndex ] ;
|
|
1471
|
+
tableCell = new documentParts.TableCell() ;
|
|
1472
|
+
tableCell.column = columnIndex ;
|
|
1473
|
+
tableCell.sx = column?.sx || - 1 ;
|
|
1474
|
+
tableCell.ex = column?.ex || - 1 ;
|
|
1475
|
+
tableRow.parts.push( tableCell ) ;
|
|
1476
|
+
}
|
|
1477
|
+
}
|
|
1339
1478
|
}
|
|
1340
1479
|
|
|
1341
1480
|
|
|
@@ -1359,9 +1498,7 @@ function parseInlineChildrenOfParent( str , ctx , parent , blockEnd , trim = fal
|
|
|
1359
1498
|
// Try to parse non-block content
|
|
1360
1499
|
function parseInline( str , ctx , blockEnd , trim = false ) {
|
|
1361
1500
|
//console.log( "parseInline() -- remaining:" , ctx.i , str.slice( ctx.i ) ) ;
|
|
1362
|
-
var
|
|
1363
|
-
|
|
1364
|
-
scanEnd = blockEnd = blockEnd ?? searchEndOfLine( str , ctx.i ) ;
|
|
1501
|
+
var scanEnd = blockEnd = blockEnd ?? searchEndOfLine( str , ctx.i ) ;
|
|
1365
1502
|
|
|
1366
1503
|
if ( trim ) {
|
|
1367
1504
|
let first = searchNextNotInSet( str , ctx.i , blockEnd , WHITE_SPACES ) ;
|
|
@@ -1647,7 +1784,7 @@ function parseInfotipedText( str , ctx , scanEnd ) {
|
|
|
1647
1784
|
ctx.iStartOfInlineChunk = ctx.i + 1 ;
|
|
1648
1785
|
|
|
1649
1786
|
if ( ! href && ! hint ) {
|
|
1650
|
-
infotipedText.href = StructuredDocument.getText( infotipedText
|
|
1787
|
+
infotipedText.href = StructuredDocument.getText( infotipedText ) ;
|
|
1651
1788
|
}
|
|
1652
1789
|
}
|
|
1653
1790
|
|
|
@@ -2001,7 +2138,7 @@ function searchBlockSwitchCloser( str , i , closer , closerMinStreak = 1 , end =
|
|
|
2001
2138
|
Same that searchBlockSwitchCloser() but with a callback function.
|
|
2002
2139
|
*/
|
|
2003
2140
|
function searchFixedBlockSwitchCloser( str , i , fixed , end = str.length ) {
|
|
2004
|
-
var
|
|
2141
|
+
var j , failed ;
|
|
2005
2142
|
|
|
2006
2143
|
while ( i < end ) {
|
|
2007
2144
|
// Search next line
|
package/lib/documentParts.js
CHANGED
|
@@ -33,13 +33,17 @@ module.exports = documentParts ;
|
|
|
33
33
|
|
|
34
34
|
|
|
35
35
|
|
|
36
|
-
function Part() {
|
|
36
|
+
function Part() {
|
|
37
|
+
this.id = null ;
|
|
38
|
+
}
|
|
37
39
|
|
|
38
40
|
documentParts.Part = Part ;
|
|
39
41
|
|
|
40
42
|
|
|
41
43
|
|
|
42
|
-
function InlinePart() {
|
|
44
|
+
function InlinePart() {
|
|
45
|
+
Part.call( this ) ;
|
|
46
|
+
}
|
|
43
47
|
|
|
44
48
|
InlinePart.prototype = Object.create( Part.prototype ) ;
|
|
45
49
|
InlinePart.prototype.constructor = InlinePart ;
|
|
@@ -48,6 +52,7 @@ documentParts.InlinePart = InlinePart ;
|
|
|
48
52
|
|
|
49
53
|
|
|
50
54
|
function InlineContainerPart() {
|
|
55
|
+
Part.call( this ) ;
|
|
51
56
|
this.parts = [] ;
|
|
52
57
|
}
|
|
53
58
|
|
|
@@ -58,6 +63,7 @@ documentParts.InlineContainerPart = InlineContainerPart ;
|
|
|
58
63
|
|
|
59
64
|
|
|
60
65
|
function InlineTextPart( text ) {
|
|
66
|
+
Part.call( this ) ;
|
|
61
67
|
this.text = text ;
|
|
62
68
|
}
|
|
63
69
|
|
|
@@ -67,7 +73,9 @@ documentParts.InlineTextPart = InlineTextPart ;
|
|
|
67
73
|
|
|
68
74
|
|
|
69
75
|
|
|
70
|
-
function BlockPart() {
|
|
76
|
+
function BlockPart() {
|
|
77
|
+
Part.call( this ) ;
|
|
78
|
+
}
|
|
71
79
|
|
|
72
80
|
BlockPart.prototype = Object.create( Part.prototype ) ;
|
|
73
81
|
BlockPart.prototype.constructor = BlockPart ;
|
|
@@ -76,6 +84,7 @@ documentParts.BlockPart = BlockPart ;
|
|
|
76
84
|
|
|
77
85
|
|
|
78
86
|
function BlockContainerPart() {
|
|
87
|
+
Part.call( this ) ;
|
|
79
88
|
this.parts = [] ;
|
|
80
89
|
}
|
|
81
90
|
|
|
@@ -362,6 +371,18 @@ documentParts.Anchor = Anchor ;
|
|
|
362
371
|
|
|
363
372
|
|
|
364
373
|
|
|
374
|
+
function Special( special ) {
|
|
375
|
+
this.type = 'special' ;
|
|
376
|
+
this.special = special ;
|
|
377
|
+
BlockContainerPart.call( this ) ;
|
|
378
|
+
}
|
|
379
|
+
|
|
380
|
+
Special.prototype = Object.create( BlockContainerPart.prototype ) ;
|
|
381
|
+
Special.prototype.constructor = Special ;
|
|
382
|
+
documentParts.Special = Special ;
|
|
383
|
+
|
|
384
|
+
|
|
385
|
+
|
|
365
386
|
function ImageBlock( href , altText , float , caption , hint ) {
|
|
366
387
|
this.type = 'imageBlock' ;
|
|
367
388
|
this.href = href ;
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
/*
|
|
2
|
+
Book Source
|
|
3
|
+
|
|
4
|
+
Copyright (c) 2023 Cédric Ronvel
|
|
5
|
+
|
|
6
|
+
The MIT License (MIT)
|
|
7
|
+
|
|
8
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
9
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
10
|
+
in the Software without restriction, including without limitation the rights
|
|
11
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
12
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
13
|
+
furnished to do so, subject to the following conditions:
|
|
14
|
+
|
|
15
|
+
The above copyright notice and this permission notice shall be included in all
|
|
16
|
+
copies or substantial portions of the Software.
|
|
17
|
+
|
|
18
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
19
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
20
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
21
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
22
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
23
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
24
|
+
SOFTWARE.
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
"use strict" ;
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
const StructuredDocument = require( './StructuredDocument.js' ) ;
|
|
32
|
+
const documentParts = require( './documentParts.js' ) ;
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
exports.autoId = ( structuredDocument , object , params , data ) => {
|
|
37
|
+
if ( ! params.types.has( object.type ) ) { return ; }
|
|
38
|
+
|
|
39
|
+
let text = StructuredDocument.getText( object ) ;
|
|
40
|
+
let id = data.idPrefix + StructuredDocument.textToId( text ) ;
|
|
41
|
+
|
|
42
|
+
if ( data.idList.has( id ) ) {
|
|
43
|
+
let originalId = id ;
|
|
44
|
+
let count = data.idList.get( originalId ) ;
|
|
45
|
+
count ++ ;
|
|
46
|
+
id = originalId + '_' + count ;
|
|
47
|
+
|
|
48
|
+
while ( data.idList.has( id ) ) {
|
|
49
|
+
count ++ ;
|
|
50
|
+
id = originalId + '_' + count ;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
data.idList.set( originalId , count ) ;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
// Always add the current ID, even if originalId was added too
|
|
57
|
+
data.idList.set( id , 1 ) ;
|
|
58
|
+
|
|
59
|
+
object.id = id ;
|
|
60
|
+
} ;
|
|
61
|
+
|
|
62
|
+
const DEFAULT_AUTO_ID_TYPES = new Set( [ 'header' ] ) ;
|
|
63
|
+
|
|
64
|
+
exports.autoId.init = ( structuredDocument , params , data ) => {
|
|
65
|
+
if ( Array.isArray( params.types ) ) { params.types = new Set( params.types ) ; }
|
|
66
|
+
else if ( ! params.types || ! ( params.types instanceof Set ) ) { params.types = DEFAULT_AUTO_ID_TYPES ; }
|
|
67
|
+
|
|
68
|
+
if ( data.idPrefix === undefined ) { data.idPrefix = params.idPrefix || '' ; }
|
|
69
|
+
|
|
70
|
+
data.idList = new Map() ;
|
|
71
|
+
} ;
|
|
72
|
+
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
exports.summary = ( structuredDocument , object , params , data ) => {
|
|
76
|
+
if ( object.type === 'special' ) {
|
|
77
|
+
switch ( object.special ) {
|
|
78
|
+
case 'summary' :
|
|
79
|
+
data.summaryObjects.push( object ) ;
|
|
80
|
+
break ;
|
|
81
|
+
case 'summary-start' :
|
|
82
|
+
resetSummary( data ) ;
|
|
83
|
+
break ;
|
|
84
|
+
case 'summary-end' :
|
|
85
|
+
data.summaryEnded = true ;
|
|
86
|
+
break ;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
return ;
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
if ( data.summaryEnded || object.type !== 'header' || object.level > params.maxLevel ) { return ; }
|
|
93
|
+
|
|
94
|
+
let item = new documentParts.ListItem( object.level - 1 ) ;
|
|
95
|
+
let link = new documentParts.Link( '#' + object.id ) ;
|
|
96
|
+
item.parts.push( link ) ;
|
|
97
|
+
let text = new documentParts.Text( StructuredDocument.getText( object ) ) ;
|
|
98
|
+
link.parts.push( text ) ;
|
|
99
|
+
|
|
100
|
+
if ( ! data.summaryHeaderLevelStack.length ) {
|
|
101
|
+
data.summaryHeaderLevelStack.push( object.level ) ;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
let lastListLevel = data.summaryHeaderLevelStack.length - 1 ;
|
|
105
|
+
let lastHeaderLevel = data.summaryHeaderLevelStack[ lastListLevel ] ;
|
|
106
|
+
|
|
107
|
+
while ( object.level < lastHeaderLevel && lastListLevel > 0 ) {
|
|
108
|
+
lastListLevel -- ;
|
|
109
|
+
lastHeaderLevel = data.summaryHeaderLevelStack[ lastListLevel ] ;
|
|
110
|
+
data.summaryHeaderLevelStack.length = data.summaryListStack.length = lastListLevel + 1 ;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
if ( object.level > lastHeaderLevel ) {
|
|
114
|
+
let parentList = data.summaryListStack[ lastListLevel ] ;
|
|
115
|
+
let currentList = new documentParts.List( object.level - 1 ) ;
|
|
116
|
+
data.summaryListStack.push( currentList ) ;
|
|
117
|
+
data.summaryHeaderLevelStack.push( object.level ) ;
|
|
118
|
+
currentList.parts.push( item ) ;
|
|
119
|
+
parentList.parts.push( currentList ) ;
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
// It's equal OR the doc is not well-formed and it's less, nevertheless, we just act as if it's equal
|
|
123
|
+
let currentList = data.summaryListStack[ lastListLevel ] ;
|
|
124
|
+
currentList.parts.push( item ) ;
|
|
125
|
+
}
|
|
126
|
+
} ;
|
|
127
|
+
|
|
128
|
+
exports.summary.init = ( structuredDocument , params , data ) => {
|
|
129
|
+
params.maxLevel = params.maxLevel || Infinity ;
|
|
130
|
+
data.summaryObjects = [] ;
|
|
131
|
+
resetSummary( data ) ;
|
|
132
|
+
} ;
|
|
133
|
+
|
|
134
|
+
function resetSummary( data ) {
|
|
135
|
+
data.summaryList = new documentParts.List( 0 ) ;
|
|
136
|
+
data.summaryListStack = [ data.summaryList ] ;
|
|
137
|
+
data.summaryHeaderLevelStack = [] ;
|
|
138
|
+
data.summaryEnded = false ;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
exports.summary.finalize = ( structuredDocument , params , data ) => {
|
|
142
|
+
structuredDocument.summary = data.summaryList ;
|
|
143
|
+
|
|
144
|
+
for ( let summaryObject of data.summaryObjects ) {
|
|
145
|
+
summaryObject.parts.push( data.summaryList ) ;
|
|
146
|
+
}
|
|
147
|
+
} ;
|
|
148
|
+
|
|
149
|
+
exports.summary.require = [ 'autoId' ] ;
|
|
150
|
+
|
package/package.json
CHANGED
package/.eslintrc.js
DELETED
|
@@ -1,168 +0,0 @@
|
|
|
1
|
-
module.exports = {
|
|
2
|
-
'root': true ,
|
|
3
|
-
'env': {
|
|
4
|
-
'browser': true ,
|
|
5
|
-
'node': true ,
|
|
6
|
-
'es6': true ,
|
|
7
|
-
'es2022': true
|
|
8
|
-
} ,
|
|
9
|
-
'parserOptions': {
|
|
10
|
-
'ecmaVersion': 2022
|
|
11
|
-
} ,
|
|
12
|
-
'extends': [ 'eslint:recommended' ] ,
|
|
13
|
-
'ignorePatterns': [ "*.min.js" ] ,
|
|
14
|
-
'rules': {
|
|
15
|
-
|
|
16
|
-
/*
|
|
17
|
-
Bad code -- detect anything that can be broken or lead to bugs
|
|
18
|
-
*/
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
'strict': [ 'error' , 'global' ] ,
|
|
23
|
-
'unicode-bom': [ 'error' , 'never' ] ,
|
|
24
|
-
'radix': 'error' ,
|
|
25
|
-
'eqeqeq': 'error' ,
|
|
26
|
-
'consistent-return': 'off' ,
|
|
27
|
-
'valid-typeof': 'error' ,
|
|
28
|
-
'no-unneeded-ternary': 'error' ,
|
|
29
|
-
'no-unused-vars': 'warn' , // During development phase, it's boring to clean unused var since they can be used later
|
|
30
|
-
'no-lonely-if': 'off' , // Can hurt semantic programming
|
|
31
|
-
'no-nested-ternary': 'off' , // Now I use the streamlined ternary operator a lot
|
|
32
|
-
'no-shadow': 'error' ,
|
|
33
|
-
'no-shadow-restricted-names': 'error' ,
|
|
34
|
-
'require-atomic-updates': 'off' , // check for possible race condition on assignment, interesting but too nitpicky
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
/*
|
|
39
|
-
Code preferences
|
|
40
|
-
*/
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
'prefer-arrow-callback': 'error' ,
|
|
45
|
-
'prefer-spread': 'warn' ,
|
|
46
|
-
'prefer-rest-params': 'warn' ,
|
|
47
|
-
'no-control-regex': 'off' , // because thing like \x00 are considered like a control even if escaped...
|
|
48
|
-
'no-fallthrough': 'off' ,
|
|
49
|
-
'no-empty': [ 'error' , {
|
|
50
|
-
'allowEmptyCatch': true
|
|
51
|
-
} ] ,
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
/*
|
|
56
|
-
Coding styles -- cosmetic rules and opinionated preferences
|
|
57
|
-
*/
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
// Indent & spaces (general)
|
|
62
|
-
'indent': [ 'error' , 'tab' , {
|
|
63
|
-
'SwitchCase': 1 ,
|
|
64
|
-
'MemberExpression': 1 ,
|
|
65
|
-
'flatTernaryExpressions': true
|
|
66
|
-
} ] ,
|
|
67
|
-
'newline-per-chained-call': 'off',
|
|
68
|
-
'no-multi-spaces': 'off' ,
|
|
69
|
-
'block-spacing': 'error' ,
|
|
70
|
-
'comma-spacing': [ 'error' , {
|
|
71
|
-
'before': true ,
|
|
72
|
-
'after': true
|
|
73
|
-
} ] ,
|
|
74
|
-
'no-whitespace-before-property': 'error' ,
|
|
75
|
-
'space-before-blocks': 'error' ,
|
|
76
|
-
'space-before-function-paren': [ 'error' , {
|
|
77
|
-
'anonymous': 'never',
|
|
78
|
-
'named': 'never',
|
|
79
|
-
'asyncArrow': 'always'
|
|
80
|
-
} ] ,
|
|
81
|
-
'space-infix-ops': 'error' ,
|
|
82
|
-
'space-unary-ops': [ 'error' , {
|
|
83
|
-
'words': true ,
|
|
84
|
-
'nonwords': true ,
|
|
85
|
-
'overrides': {
|
|
86
|
-
//'-': false ,
|
|
87
|
-
}
|
|
88
|
-
} ] ,
|
|
89
|
-
'space-in-parens': [ 'error' , 'always' , {
|
|
90
|
-
'exceptions': [ 'empty' ]
|
|
91
|
-
} ] ,
|
|
92
|
-
'no-trailing-spaces': 'error' ,
|
|
93
|
-
'switch-colon-spacing': [ 'error' , {
|
|
94
|
-
'after': true ,
|
|
95
|
-
'before': true
|
|
96
|
-
} ] ,
|
|
97
|
-
'arrow-spacing': 'error' ,
|
|
98
|
-
'rest-spread-spacing': [ 'error' , 'always' ] ,
|
|
99
|
-
/* Troublesome with commented line of code
|
|
100
|
-
'spaced-comment': [ 'error' , 'always' , {
|
|
101
|
-
'line': {
|
|
102
|
-
'markers': [ '/' ],
|
|
103
|
-
'exceptions': [ '-', '*', '/' ]
|
|
104
|
-
} ,
|
|
105
|
-
'block': {
|
|
106
|
-
'exceptions': [ '*' ] ,
|
|
107
|
-
'balanced': true
|
|
108
|
-
}
|
|
109
|
-
} ] ,
|
|
110
|
-
*/
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
// Semi-colon
|
|
114
|
-
'semi': [ 'error' , 'always' ] ,
|
|
115
|
-
'semi-style': [ 'error' , 'last' ] ,
|
|
116
|
-
'semi-spacing': [ 'error' , {
|
|
117
|
-
'before': true ,
|
|
118
|
-
'after': true
|
|
119
|
-
} ] ,
|
|
120
|
-
|
|
121
|
-
// Objects
|
|
122
|
-
'key-spacing': [ 'error' , {
|
|
123
|
-
'beforeColon': false ,
|
|
124
|
-
'afterColon': true ,
|
|
125
|
-
'mode': 'strict'
|
|
126
|
-
} ] ,
|
|
127
|
-
'object-curly-newline': [ 'error' , {
|
|
128
|
-
'ObjectExpression' : {
|
|
129
|
-
'consistent': true ,
|
|
130
|
-
'minProperties': 4
|
|
131
|
-
} ,
|
|
132
|
-
'ObjectPattern' : {
|
|
133
|
-
// object destructuring assigment
|
|
134
|
-
'consistent': true ,
|
|
135
|
-
'minProperties': 8
|
|
136
|
-
}
|
|
137
|
-
} ] ,
|
|
138
|
-
'object-curly-spacing': [ 'error' , 'always' ] ,
|
|
139
|
-
'object-property-newline': [ 'error' , { 'allowMultiplePropertiesPerLine': true } ] ,
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
// Arrays
|
|
143
|
-
'array-bracket-newline': [ 'error' , 'consistent' ] ,
|
|
144
|
-
//'array-element-newline': [ 'error' , { 'multiline': true , 'minItems': 5 } ] ,
|
|
145
|
-
'array-bracket-spacing': [ 'error' , 'always' ],
|
|
146
|
-
|
|
147
|
-
'brace-style': [ 'error' , 'stroustrup' , {
|
|
148
|
-
'allowSingleLine': true
|
|
149
|
-
} ] ,
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
// Misc style
|
|
153
|
-
'no-else-return': 'warn' ,
|
|
154
|
-
'comma-dangle': [ 'error' , 'never' ] ,
|
|
155
|
-
'quotes': 'off' ,
|
|
156
|
-
'camelcase': 'warn' ,
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
/*
|
|
161
|
-
Method limitation
|
|
162
|
-
*/
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
'no-console': 'off'
|
|
167
|
-
}
|
|
168
|
-
} ;
|
package/Makefile
DELETED
|
@@ -1,112 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
# User rules
|
|
5
|
-
|
|
6
|
-
# The first rule is the default rule, when invoking "make" without argument...
|
|
7
|
-
# Build every buildable things
|
|
8
|
-
#all: install doc browser
|
|
9
|
-
all: install doc
|
|
10
|
-
|
|
11
|
-
# Just install things so it works, basicaly: it just performs a "npm install --production" ATM
|
|
12
|
-
install: log/npm-install.log
|
|
13
|
-
|
|
14
|
-
# Just install things so it works, basicaly: it just performs a "npm install" ATM
|
|
15
|
-
dev-install: log/npm-dev-install.log
|
|
16
|
-
|
|
17
|
-
# Build
|
|
18
|
-
#build: browser
|
|
19
|
-
|
|
20
|
-
# Build the browser lib
|
|
21
|
-
#browser: browser/svg-kit.js browser/svg-kit.min.js
|
|
22
|
-
|
|
23
|
-
# This run the JsHint & Mocha BDD test, display it to STDOUT & save it to log/mocha.log and log/jshint.log
|
|
24
|
-
test: log/jshint.log log/mocha.log
|
|
25
|
-
|
|
26
|
-
# This run the JsHint, display it to STDOUT & save it to log/jshint.log
|
|
27
|
-
lint: log/jshint.log
|
|
28
|
-
|
|
29
|
-
# This run the Mocha BDD test, display it to STDOUT & save it to log/mocha.log
|
|
30
|
-
unit: log/mocha.log
|
|
31
|
-
|
|
32
|
-
# This build the doc and README.md
|
|
33
|
-
doc: README.md
|
|
34
|
-
|
|
35
|
-
# This publish to NPM and push to Github, if we are on master branch only
|
|
36
|
-
publish: log/npm-publish.log log/github-push.log
|
|
37
|
-
|
|
38
|
-
# Clean temporary things, or things that can be automatically regenerated
|
|
39
|
-
clean: clean-all
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
# Variables
|
|
44
|
-
|
|
45
|
-
BROWSERIFY=browserify
|
|
46
|
-
UGLIFY=uglifyjs
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
# Files rules
|
|
51
|
-
|
|
52
|
-
# Build the browser lib
|
|
53
|
-
#browser/svg-kit.js: lib/*.js lib/*/*.js
|
|
54
|
-
# ${BROWSERIFY} lib/svg-kit.js -i fs -i image-size -s svgKit -o browser/svg-kit.js
|
|
55
|
-
|
|
56
|
-
# Build the browser minified lib
|
|
57
|
-
#browser/svg-kit.min.js: browser/svg-kit.js
|
|
58
|
-
# ${UGLIFY} browser/svg-kit.js -o browser/svg-kit.min.js -m
|
|
59
|
-
|
|
60
|
-
# JsHint STDOUT test
|
|
61
|
-
log/jshint.log: log/npm-dev-install.log lib/*.js test/*.js
|
|
62
|
-
${JSHINT} lib/*.js test/*.js | tee log/jshint.log ; exit $${PIPESTATUS[0]}
|
|
63
|
-
|
|
64
|
-
# Mocha BDD STDOUT test
|
|
65
|
-
log/mocha.log: log/npm-dev-install.log lib/*.js test/*.js
|
|
66
|
-
cd test ; ${MOCHA} *.js -R spec | tee ../log/mocha.log ; exit $${PIPESTATUS[0]}
|
|
67
|
-
|
|
68
|
-
# README
|
|
69
|
-
README.md: documentation.md
|
|
70
|
-
cat documentation.md > README.md
|
|
71
|
-
|
|
72
|
-
# Mocha Markdown BDD spec
|
|
73
|
-
bdd-spec.md: log/npm-dev-install.log lib/*.js test/*.js
|
|
74
|
-
cd test ; ${MOCHA} *.js -R markdown > ../bdd-spec.md
|
|
75
|
-
|
|
76
|
-
# Upgrade version in package.json
|
|
77
|
-
log/upgrade-package.log: lib/*.js test/*.js documentation.md
|
|
78
|
-
npm version patch -m "Upgrade package.json version to %s" | tee log/upgrade-package.log ; exit $${PIPESTATUS[0]}
|
|
79
|
-
|
|
80
|
-
# Publish to NPM
|
|
81
|
-
log/npm-publish.log: check-if-master-branch log/upgrade-package.log
|
|
82
|
-
npm publish | tee log/npm-publish.log ; exit $${PIPESTATUS[0]}
|
|
83
|
-
|
|
84
|
-
# Push to Github/master
|
|
85
|
-
log/github-push.log: lib/*.js test/*.js package.json
|
|
86
|
-
#'npm version patch' create the git tag by itself...
|
|
87
|
-
#git tag v`cat package.json | grep version | sed -r 's/.*"([0-9.]*)".*/\1/'`
|
|
88
|
-
git push origin master --tags | tee log/github-push.log ; exit $${PIPESTATUS[0]}
|
|
89
|
-
|
|
90
|
-
# NPM install
|
|
91
|
-
log/npm-install.log: package.json
|
|
92
|
-
npm install --production | tee log/npm-install.log ; exit $${PIPESTATUS[0]}
|
|
93
|
-
|
|
94
|
-
# NPM install for developpement usage
|
|
95
|
-
log/npm-dev-install.log: package.json
|
|
96
|
-
npm install | tee log/npm-dev-install.log ; exit $${PIPESTATUS[0]}
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
# PHONY rules
|
|
101
|
-
|
|
102
|
-
.PHONY: clean-all check-if-master-branch
|
|
103
|
-
|
|
104
|
-
# Delete files, mostly log and non-versioned files
|
|
105
|
-
clean-all:
|
|
106
|
-
rm -rf log/*.log README.md bdd-spec.md node_modules
|
|
107
|
-
|
|
108
|
-
# This will fail if we are not on master branch (grep exit 1 if nothing found)
|
|
109
|
-
check-if-master-branch:
|
|
110
|
-
git branch | grep "^* master$$"
|
|
111
|
-
|
|
112
|
-
|
package/documentation.md
DELETED
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
# Book Source
|
|
3
|
-
|
|
4
|
-
Book Source is a Lightweight Markup Language similar to Markdown.
|
|
5
|
-
|
|
6
|
-
This is the parser, you may want to add a renderer, like the [Book Source HTML renderer](https://github.com/cronvel/book-source-html-renderer).
|
|
7
|
-
|
|
8
|
-
New renderers can easily be created.
|
|
9
|
-
|
|
10
|
-
The parser has zero regex.
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
## Book Source syntax
|
|
15
|
-
|
|
16
|
-
TODO
|
|
17
|
-
|