@@ -8,6 +8,8 @@ use std::{io, path::PathBuf};
88use fs_err as fs;
99use itertools:: Itertools ;
1010use moss:: Dependency ;
11+ use serde:: Serialize ;
12+ use std:: io:: Write ;
1113use thiserror:: Error ;
1214use url:: Url ;
1315
@@ -20,6 +22,22 @@ mod build;
2022mod metadata;
2123mod upstream;
2224
25+ #[ derive( Serialize ) ]
26+ struct Monitoring {
27+ releases : Releases ,
28+ security : Security ,
29+ }
30+
31+ #[ derive( Serialize ) ]
32+ struct Releases {
33+ id : Option < u16 > ,
34+ }
35+
36+ #[ derive( Serialize ) ]
37+ struct Security {
38+ cpe : Option < String > ,
39+ }
40+
2341pub struct Drafter {
2442 upstreams : Vec < Url > ,
2543}
@@ -29,6 +47,33 @@ impl Drafter {
2947 Self { upstreams }
3048 }
3149
50+ pub fn write_monitoring ( & self ) -> Result < String , Error > {
51+ let monitoring_template = Monitoring {
52+ releases : Releases { id : None } ,
53+ security : Security { cpe : None } ,
54+ } ;
55+
56+ let mut yaml_string = serde_yaml:: to_string ( & monitoring_template) . expect ( "Failed to serialize to YAML" ) ;
57+
58+ let id_string = "id: null" ;
59+ let id_marker = yaml_string. find ( id_string) . expect ( "releases id marker not found" ) ;
60+ let id_help_text = " # https://release-monitoring.org/ and use the numeric id in the url of project" ;
61+
62+ // append_str at marker instead of insert
63+ yaml_string. insert_str ( id_marker + id_string. len ( ) , id_help_text) ;
64+
65+ let cpe_string = "cpe: null" ;
66+ let cpe_marker = yaml_string. find ( cpe_string) . expect ( "security cpe marker not found" ) ;
67+ let cpe_help_text = " # Use the cpesearch bash macro and insert [ { - vendor: foo, product: bar } ] if found" ;
68+
69+ yaml_string. insert_str ( cpe_marker + cpe_string. len ( ) , cpe_help_text) ;
70+
71+ let mut file = std:: fs:: File :: create ( "monitoring.yaml" ) ?;
72+ file. write_all ( yaml_string. as_bytes ( ) ) ?;
73+ println ! ( "Wrote template 'monitoring.yaml' file" ) ;
74+ Ok ( yaml_string)
75+ }
76+
3277 pub fn run ( & self ) -> Result < String , Error > {
3378 // TODO: Use tempdir
3479 let extract_root = PathBuf :: from ( "/tmp/boulder-new" ) ;
@@ -42,7 +87,7 @@ impl Drafter {
4287 // Enumerate all extracted files
4388 let files = util:: enumerate_files ( & extract_root, |_| true ) ?
4489 . into_iter ( )
45- . map ( |path| File {
90+ . map ( |path| DrafterFile {
4691 path,
4792 extract_root : & extract_root,
4893 } )
@@ -90,6 +135,8 @@ license : UPDATE LICENSE
90135 metadata. upstreams( ) ,
91136 ) ;
92137
138+ self . write_monitoring ( ) ?;
139+
93140 Ok ( template)
94141 }
95142}
@@ -104,12 +151,12 @@ fn builddeps(deps: impl IntoIterator<Item = Dependency>) -> String {
104151 }
105152}
106153
107- pub struct File < ' a > {
154+ pub struct DrafterFile < ' a > {
108155 pub path : PathBuf ,
109156 pub extract_root : & ' a Path ,
110157}
111158
112- impl File < ' _ > {
159+ impl DrafterFile < ' _ > {
113160 // The depth of a file relative to it's extracted archive
114161 pub fn depth ( & self ) -> usize {
115162 let relative = self . path . strip_prefix ( self . extract_root ) . unwrap_or ( & self . path ) ;
@@ -145,7 +192,7 @@ mod test {
145192 fn test_file_depth ( ) {
146193 let extract_root = Path :: new ( "/tmp/test" ) ;
147194
148- let file = File {
195+ let file = DrafterFile {
149196 path : PathBuf :: from ( "/tmp/test/some_archive/meson.build" ) ,
150197 extract_root,
151198 } ;
0 commit comments