@@ -33,12 +33,15 @@ const THEME_CONTRIB_GUIDELINESS = `
33
33
34
34
\r> Also, note that if this theme is exclusively for your personal use, then instead of adding it to our theme collection, you can use card [customization options](https://github.com/anuraghazra/github-readme-stats#customization).
35
35
` ;
36
- const REQUIRED_COLOR_PROPS = [
37
- "title_color" ,
38
- "icon_color" ,
39
- "text_color" ,
40
- "bg_color" ,
41
- ] ;
36
+ const COLOR_PROPS = {
37
+ title_color :6 ,
38
+ icon_color :6 ,
39
+ text_color :6 ,
40
+ bg_color :8 ,
41
+ border_color :6 ,
42
+ } ;
43
+ const ACCEPTED_COLOR_PROPS = Object . keys ( COLOR_PROPS ) ;
44
+ const REQUIRED_COLOR_PROPS = ACCEPTED_COLOR_PROPS . slice ( 0 , 4 ) ;
42
45
const INVALID_REVIEW_COMMENT = ( commentUrl ) =>
43
46
`Some themes are invalid. See the [Automated Theme Preview](${ commentUrl } ) comment above for more information.` ;
44
47
@@ -271,11 +274,11 @@ const parseJSON = (json) => {
271
274
}
272
275
} catch ( error ) {
273
276
let parsedJson = json
274
- . split ( / (?: \s * ) ( } \s * , ? ) (?: \s * ) (? = \s * [ a - z _ " ] + : + ) / )
277
+ . split ( / ( [ \s \r \s ] * } [ \s \r \s ] * , [ \s \r \s ] * ) (? = [ \w " - ] + : ) / )
275
278
. filter ( ( x ) => typeof x !== "string" || ! ! x . trim ( ) ) ;
276
279
if ( parsedJson [ 0 ] . replace ( / \s + / g, "" ) === "}," ) {
277
280
parsedJson [ 0 ] = "}," ;
278
- if ( ! / \s * } \s * , ? \s * $ / . test ( parsedJson [ 0 ] ) ) {
281
+ if ( ! / \s * } \s * , ? \s * $ / . test ( parsedJson [ 1 ] ) ) {
279
282
parsedJson . push ( parsedJson . shift ( ) ) ;
280
283
} else {
281
284
parsedJson . shift ( ) ;
@@ -299,7 +302,7 @@ const themeNameAlreadyExists = (name) => {
299
302
/**
300
303
* Main function.
301
304
*/
302
- const run = async ( ) => {
305
+ export const run = async ( prNumber ) => {
303
306
try {
304
307
const dryRun = process . env . DRY_RUN === "true" || false ;
305
308
debug ( "Retrieve action information from context..." ) ;
@@ -310,7 +313,7 @@ const run = async () => {
310
313
` ;
311
314
const ccc = new ColorContrastChecker ( ) ;
312
315
const octokit = github . getOctokit ( getGithubToken ( ) ) ;
313
- const pullRequestId = getPrNumber ( ) ;
316
+ const pullRequestId = prNumber ? prNumber : getPrNumber ( ) ;
314
317
const commenter = getCommenter ( ) ;
315
318
const { owner, repo} = getRepoInfo ( github . context ) ;
316
319
debug ( `Owner:${ owner } ` ) ;
@@ -387,10 +390,19 @@ const run = async () => {
387
390
const missingKeys = REQUIRED_COLOR_PROPS . filter (
388
391
( x ) => ! Object . keys ( colors ) . includes ( x ) ,
389
392
) ;
390
- if ( missingKeys . length > 0 ) {
393
+ const extraKeys = Object . keys ( colors ) . filter (
394
+ ( x ) => ! ACCEPTED_COLOR_PROPS . includes ( x ) ,
395
+ ) ;
396
+ if ( missingKeys . length > 0 || extraKeys . length > 0 ) {
391
397
for ( const missingKey of missingKeys ) {
392
398
errors . push ( `Theme color properties \`${ missingKey } \` are missing` ) ;
393
399
}
400
+
401
+ for ( const extraKey of extraKeys ) {
402
+ warnings . push (
403
+ `Theme color properties \`${ extraKey } \` is not supported` ,
404
+ ) ;
405
+ }
394
406
invalidColors = true ;
395
407
} else {
396
408
for ( const [ colorKey , colorValue ] of Object . entries ( colors ) ) {
@@ -399,6 +411,11 @@ const run = async () => {
399
411
`Theme color property \`${ colorKey } \` should not start with '#'` ,
400
412
) ;
401
413
invalidColors = true ;
414
+ } else if ( colorValue . length > COLOR_PROPS [ colorKey ] ) {
415
+ errors . push (
416
+ `Theme color property \`${ colorKey } \` can not be longer than \`${ COLOR_PROPS [ colorKey ] } \` characters` ,
417
+ ) ;
418
+ invalidColors = true ;
402
419
} else if ( ! isValidHexColor ( colorValue ) ) {
403
420
errors . push (
404
421
`Theme color property \`${ colorKey } \` is not a valid hex color: <code>#${ colorValue } </code>` ,
@@ -437,8 +454,10 @@ const run = async () => {
437
454
text_color :[ textColor , bgColor ] ,
438
455
} ;
439
456
Object . keys ( colorPairs ) . forEach ( ( item ) => {
440
- const color1 = colorPairs [ item ] [ 0 ] ;
441
- const color2 = colorPairs [ item ] [ 1 ] ;
457
+ let color1 = colorPairs [ item ] [ 0 ] ;
458
+ let color2 = colorPairs [ item ] [ 1 ] ;
459
+ color1 = color1 . length === 4 ?color1 . slice ( 0 , 3 ) :color1 . slice ( 0 , 6 ) ;
460
+ color2 = color2 . length === 4 ?color2 . slice ( 0 , 3 ) :color2 . slice ( 0 , 6 ) ;
442
461
if ( ! ccc . isLevelAA ( `#${ color1 } ` , `#${ color2 } ` ) ) {
443
462
const permalink = getWebAimLink ( color1 , color2 ) ;
444
463
warnings . push (
@@ -543,4 +562,6 @@ const run = async () => {
543
562
}
544
563
} ;
545
564
546
- run ( ) ;
565
+ if ( typeof require !== "undefined" && require . main === module ) {
566
+ run ( ) ;
567
+ }