Skip to content

Commit 49b902f

Browse files
committed
include directories in grouped licensing information
1 parent 6473ff1 commit 49b902f

File tree

2 files changed

+72
-30
lines changed

2 files changed

+72
-30
lines changed

src/tools/collect-license-metadata/src/path_tree.rs

Lines changed: 69 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ pub(crate) enum Node<L> {
1313
Root { childs: Vec<Node<L>> },
1414
Directory { name: PathBuf, childs: Vec<Node<L>>, license: Option<L> },
1515
File { name: PathBuf, license: L },
16-
FileGroup { names: Vec<PathBuf>, license: L },
16+
Group { files: Vec<PathBuf>, directories: Vec<PathBuf>, license: L },
1717
Empty,
1818
}
1919

@@ -22,7 +22,7 @@ impl Node<LicenseId> {
2222
self.merge_directories();
2323
self.collapse_in_licensed_directories();
2424
self.merge_directory_licenses();
25-
self.merge_file_groups();
25+
self.merge_groups();
2626
self.remove_empty();
2727
}
2828

@@ -64,8 +64,8 @@ impl Node<LicenseId> {
6464
Node::Root { .. } => {
6565
panic!("can't have a root inside another element");
6666
}
67-
Node::FileGroup { .. } => {
68-
panic!("FileGroup should not be present at this stage");
67+
Node::Group { .. } => {
68+
panic!("Group should not be present at this stage");
6969
}
7070
Node::Directory { license: Some(_), .. } => {
7171
panic!("license should not be set at this stage");
@@ -86,8 +86,8 @@ impl Node<LicenseId> {
8686
}
8787
Node::Empty => {}
8888
Node::File { .. } => {}
89-
Node::FileGroup { .. } => {
90-
panic!("FileGroup should not be present at this stage");
89+
Node::Group { .. } => {
90+
panic!("Group should not be present at this stage");
9191
}
9292
Node::Directory { license: Some(_), .. } => {
9393
panic!("license should not be set at this stage");
@@ -132,7 +132,7 @@ impl Node<LicenseId> {
132132
}
133133
}
134134
Node::File { .. } => {}
135-
Node::FileGroup { .. } => {}
135+
Node::Group { .. } => panic!("group should not be present at this stage"),
136136
Node::Empty => {}
137137
}
138138
}
@@ -165,8 +165,8 @@ impl Node<LicenseId> {
165165
Node::Root { .. } => {
166166
panic!("can't have a root inside another element");
167167
}
168-
Node::FileGroup { .. } => {
169-
panic!("FileGroup should not be present at this stage");
168+
Node::Group { .. } => {
169+
panic!("Group should not be present at this stage");
170170
}
171171
Node::Directory { name: child_child_name, .. } => {
172172
*child_child_name = child_name.join(&child_child_name);
@@ -185,38 +185,74 @@ impl Node<LicenseId> {
185185
}
186186
Node::Empty => {}
187187
Node::File { .. } => {}
188-
Node::FileGroup { .. } => {}
188+
Node::Group { .. } => panic!("Group should not be present at this stage"),
189189
}
190190
}
191191

192192
/// This pass groups multiple files in a directory with the same license into a single
193-
/// "FileGroup", so that the license of all those files can be reported as a group.
193+
/// "Group", so that the license of all those files can be reported as a group.
194+
///
195+
/// This also merges directories *without exceptions*.
194196
///
195197
/// Crucially this pass runs after collapse_in_licensed_directories, so the most common license
196198
/// will already be marked as the directory's license and won't be turned into a group.
197-
fn merge_file_groups(&mut self) {
199+
fn merge_groups(&mut self) {
200+
#[derive(Default)]
201+
struct Grouped {
202+
files: Vec<PathBuf>,
203+
directories: Vec<PathBuf>,
204+
}
198205
match self {
199206
Node::Root { childs } | Node::Directory { childs, .. } => {
200-
let mut grouped = BTreeMap::new();
207+
let mut grouped: BTreeMap<LicenseId, Grouped> = BTreeMap::new();
201208

202209
for child in &mut *childs {
203-
child.merge_file_groups();
204-
if let Node::File { name, license } = child {
205-
grouped.entry(*license).or_insert_with(Vec::new).push(name.clone());
206-
*child = Node::Empty;
210+
child.merge_groups();
211+
match child {
212+
Node::Directory { name, childs, license: Some(license) } => {
213+
if childs.is_empty() {
214+
grouped
215+
.entry(*license)
216+
.or_insert_with(Grouped::default)
217+
.directories
218+
.push(name.clone());
219+
*child = Node::Empty;
220+
}
221+
}
222+
Node::File { name, license } => {
223+
grouped
224+
.entry(*license)
225+
.or_insert_with(Grouped::default)
226+
.files
227+
.push(name.clone());
228+
*child = Node::Empty;
229+
}
230+
_ => {}
207231
}
208232
}
209233

210-
for (license, mut names) in grouped.into_iter() {
211-
if names.len() == 1 {
212-
childs.push(Node::File { license, name: names.pop().unwrap() });
234+
for (license, mut grouped) in grouped.into_iter() {
235+
if grouped.files.len() + grouped.directories.len() <= 1 {
236+
if let Some(name) = grouped.files.pop() {
237+
childs.push(Node::File { license, name });
238+
} else if let Some(name) = grouped.directories.pop() {
239+
childs.push(Node::Directory {
240+
name,
241+
childs: Vec::new(),
242+
license: Some(license),
243+
});
244+
}
213245
} else {
214-
childs.push(Node::FileGroup { license, names });
246+
childs.push(Node::Group {
247+
license,
248+
files: grouped.files,
249+
directories: grouped.directories,
250+
});
215251
}
216252
}
217253
}
218254
Node::File { .. } => {}
219-
Node::FileGroup { .. } => panic!("FileGroup should not be present at this stage"),
255+
Node::Group { .. } => panic!("FileGroup should not be present at this stage"),
220256
Node::Empty => {}
221257
}
222258
}
@@ -231,7 +267,7 @@ impl Node<LicenseId> {
231267
}
232268
childs.retain(|child| !matches!(child, Node::Empty));
233269
}
234-
Node::FileGroup { .. } => {}
270+
Node::Group { .. } => {}
235271
Node::File { .. } => {}
236272
Node::Empty => {}
237273
}
@@ -278,16 +314,22 @@ pub(crate) fn expand_interned_licenses(
278314
) -> Node<&License> {
279315
match node {
280316
Node::Root { childs } => Node::Root {
281-
childs: childs.into_iter().map(|child| expand_interned_licenses(child, interner)).collect(),
317+
childs: childs
318+
.into_iter()
319+
.map(|child| expand_interned_licenses(child, interner))
320+
.collect(),
282321
},
283322
Node::Directory { name, childs, license } => Node::Directory {
284-
childs: childs.into_iter().map(|child| expand_interned_licenses(child, interner)).collect(),
323+
childs: childs
324+
.into_iter()
325+
.map(|child| expand_interned_licenses(child, interner))
326+
.collect(),
285327
license: license.map(|license| interner.resolve(license)),
286328
name,
287329
},
288330
Node::File { name, license } => Node::File { name, license: interner.resolve(license) },
289-
Node::FileGroup { names, license } => {
290-
Node::FileGroup { names, license: interner.resolve(license) }
331+
Node::Group { files, directories, license } => {
332+
Node::Group { files, directories, license: interner.resolve(license) }
291333
}
292334
Node::Empty => Node::Empty,
293335
}

src/tools/generate-copyright/src/main.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,8 +36,8 @@ fn render_recursive(node: &Node, buffer: &mut Vec<u8>, depth: usize) -> Result<(
3636
}
3737
}
3838
}
39-
Node::FileGroup { names, license } => {
40-
render_license(&prefix, names.iter(), license, buffer)?;
39+
Node::Group { files, directories, license } => {
40+
render_license(&prefix, directories.iter().chain(files.iter()), license, buffer)?;
4141
}
4242
Node::File { name, license } => {
4343
render_license(&prefix, std::iter::once(name), license, buffer)?;
@@ -76,7 +76,7 @@ pub(crate) enum Node {
7676
Root { childs: Vec<Node> },
7777
Directory { name: String, childs: Vec<Node>, license: License },
7878
File { name: String, license: License },
79-
FileGroup { names: Vec<String>, license: License },
79+
Group { files: Vec<String>, directories: Vec<String>, license: License },
8080
}
8181

8282
#[derive(serde::Deserialize)]

0 commit comments

Comments
 (0)