@@ -79,12 +79,22 @@ pub enum AttributeVariant {
79
79
NonAttributeSet ,
80
80
AttributeSet {
81
81
/// Whether the attribute is a derivation (`lib.isDerivation`)
82
- is_derivation : bool ,
82
+ derivation : Derivation ,
83
83
/// The type of `callPackage` used.
84
84
definition_variant : DefinitionVariant ,
85
85
} ,
86
86
}
87
87
88
+ /// Info about a derivation
89
+ #[ derive( Deserialize ) ]
90
+ pub enum Derivation {
91
+ NonDerivation ,
92
+ Derivation {
93
+ pname : String ,
94
+ description : Option < String > ,
95
+ } ,
96
+ }
97
+
88
98
#[ derive( Deserialize ) ]
89
99
pub enum DefinitionVariant {
90
100
/// An automatic definition by the `pkgs/by-name` overlay, though it's detected using the
@@ -261,6 +271,61 @@ pub fn check_values(
261
271
} ) )
262
272
}
263
273
274
+ /// Check the validity of a package description
275
+ fn check_description ( pname : & str , description : & Option < String > ) -> ratchet:: PackageDescription {
276
+ if let Some ( text) = description {
277
+ let lowercased = text. to_lowercase ( ) ;
278
+ ratchet:: PackageDescription {
279
+ not_capitalised : {
280
+ if let Some ( first) = text. chars ( ) . next ( ) {
281
+ if first. is_lowercase ( ) {
282
+ Loose ( text. to_owned ( ) )
283
+ } else {
284
+ Tight
285
+ }
286
+ } else {
287
+ Tight
288
+ }
289
+ } ,
290
+ starts_with_article : {
291
+ if lowercased. starts_with ( "a " )
292
+ || lowercased. starts_with ( "an " )
293
+ || lowercased. starts_with ( "the " )
294
+ {
295
+ Loose ( text. to_owned ( ) )
296
+ } else {
297
+ Tight
298
+ }
299
+ } ,
300
+ starts_with_package_name : {
301
+ if lowercased. starts_with ( & pname. to_lowercase ( ) ) {
302
+ Loose ( text. to_owned ( ) )
303
+ } else {
304
+ Tight
305
+ }
306
+ } ,
307
+ ends_with_punctuation : {
308
+ if let Some ( last) = text. chars ( ) . last ( ) {
309
+ if last. is_ascii_punctuation ( ) {
310
+ Loose ( text. to_owned ( ) )
311
+ } else {
312
+ Tight
313
+ }
314
+ } else {
315
+ Tight
316
+ }
317
+ } ,
318
+ }
319
+ } else {
320
+ ratchet:: PackageDescription {
321
+ not_capitalised : Tight ,
322
+ starts_with_article : Tight ,
323
+ starts_with_package_name : Tight ,
324
+ ends_with_punctuation : Tight ,
325
+ }
326
+ }
327
+ }
328
+
264
329
/// Handle the evaluation result for an attribute in `pkgs/by-name`, making it a validation result.
265
330
fn by_name (
266
331
nix_file_store : & mut NixFileStore ,
@@ -279,6 +344,27 @@ fn by_name(
279
344
. into ( )
280
345
} ;
281
346
347
+ let description_ratchet = match by_name_attribute {
348
+ Existing ( AttributeInfo {
349
+ attribute_variant :
350
+ AttributeVariant :: AttributeSet {
351
+ derivation :
352
+ Derivation :: Derivation {
353
+ pname : ref name,
354
+ ref description,
355
+ } ,
356
+ ..
357
+ } ,
358
+ ..
359
+ } ) => check_description ( name, description) ,
360
+ _ => ratchet:: PackageDescription {
361
+ not_capitalised : NonApplicable ,
362
+ starts_with_article : NonApplicable ,
363
+ starts_with_package_name : NonApplicable ,
364
+ ends_with_punctuation : NonApplicable ,
365
+ } ,
366
+ } ;
367
+
282
368
// At this point we know that `pkgs/by-name/fo/foo/package.nix` has to exists. This match
283
369
// decides whether the attribute `foo` is defined accordingly and whether a legacy manual
284
370
// definition could be removed.
@@ -308,16 +394,17 @@ fn by_name(
308
394
// And it's an attribute set, which allows us to get more information about it
309
395
attribute_variant :
310
396
AttributeVariant :: AttributeSet {
311
- is_derivation ,
397
+ derivation ,
312
398
definition_variant,
313
399
} ,
314
400
location,
315
401
} ) => {
316
402
// Only derivations are allowed in `pkgs/by-name`.
317
- let is_derivation_result = if is_derivation {
318
- Success ( ( ) )
319
- } else {
320
- to_validation ( ByNameErrorKind :: NonDerivation ) . map ( |_| ( ) )
403
+ let is_derivation_result = match derivation {
404
+ Derivation :: Derivation { .. } => Success ( ( ) ) ,
405
+ Derivation :: NonDerivation => {
406
+ to_validation ( ByNameErrorKind :: NonDerivation ) . map ( |_| ( ) )
407
+ }
321
408
} ;
322
409
323
410
// If the definition looks correct
@@ -399,6 +486,7 @@ fn by_name(
399
486
// once at the end with a map.
400
487
manual_definition_result. map ( |manual_definition| ratchet:: Package {
401
488
manual_definition,
489
+ description : description_ratchet,
402
490
uses_by_name : Tight ,
403
491
} ) ,
404
492
)
@@ -477,6 +565,27 @@ fn handle_non_by_name_attribute(
477
565
use ratchet:: RatchetState :: * ;
478
566
use NonByNameAttribute :: * ;
479
567
568
+ let description_ratchet = match non_by_name_attribute {
569
+ EvalSuccess ( AttributeInfo {
570
+ attribute_variant :
571
+ AttributeVariant :: AttributeSet {
572
+ derivation :
573
+ Derivation :: Derivation {
574
+ pname : ref name,
575
+ ref description,
576
+ } ,
577
+ ..
578
+ } ,
579
+ ..
580
+ } ) => check_description ( name, description) ,
581
+ _ => ratchet:: PackageDescription {
582
+ not_capitalised : NonApplicable ,
583
+ starts_with_article : NonApplicable ,
584
+ starts_with_package_name : NonApplicable ,
585
+ ends_with_punctuation : NonApplicable ,
586
+ } ,
587
+ } ;
588
+
480
589
// The ratchet state whether this attribute uses `pkgs/by-name`.
481
590
//
482
591
// This is never `Tight`, because we only either:
@@ -504,7 +613,7 @@ fn handle_non_by_name_attribute(
504
613
// are. Anything else can't be in `pkgs/by-name`.
505
614
attribute_variant : AttributeVariant :: AttributeSet {
506
615
// As of today, non-derivation attribute sets can't be in `pkgs/by-name`.
507
- is_derivation : true ,
616
+ derivation : Derivation :: Derivation { .. } ,
508
617
// Of the two definition variants, really only the manual one makes sense here.
509
618
//
510
619
// Special cases are:
@@ -601,5 +710,6 @@ fn handle_non_by_name_attribute(
601
710
// ourselves all the time to define `manual_definition`, just set it once at the end here.
602
711
manual_definition : Tight ,
603
712
uses_by_name,
713
+ description : description_ratchet,
604
714
} ) )
605
715
}
0 commit comments