cmake_parser/doc/command/project/
target_sources.rs

1use cmake_parser_derive::CMake;
2
3use crate::{
4    doc::command_scope::{CommandScope, ToCommandScope},
5    Token,
6};
7
8/// Add sources to a target.
9///
10/// Reference: <https://cmake.org/cmake/help/v3.26/command/target_sources.html>
11#[derive(CMake, Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
12#[cmake(pkg = "crate")]
13pub struct TargetSources<'t> {
14    #[cmake(positional)]
15    pub target: Token<'t>,
16    pub sources: Vec<Source<'t>>,
17}
18
19impl<'t> ToCommandScope for TargetSources<'t> {
20    fn to_command_scope(&self) -> CommandScope {
21        CommandScope::Project
22    }
23}
24
25#[derive(CMake, Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
26#[cmake(pkg = "crate", transparent)]
27pub enum Source<'t> {
28    Interface(Vec<SourceItem<'t>>),
29    Public(Vec<SourceItem<'t>>),
30    Private(Vec<SourceItem<'t>>),
31}
32
33#[derive(CMake, Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
34#[cmake(pkg = "crate", untagged)]
35pub enum SourceItem<'t> {
36    FileSet(FileSet<'t>),
37    Item(Token<'t>),
38}
39
40#[derive(CMake, Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
41#[cmake(pkg = "crate")]
42pub struct FileSet<'t> {
43    file_set: Token<'t>,
44    #[cmake(rename = "TYPE")]
45    file_set_type: Option<Token<'t>>,
46    base_dirs: Option<Vec<Token<'t>>>,
47    files: Option<Vec<Token<'t>>>,
48}
49
50#[cfg(test)]
51mod tests {
52    use super::*;
53    use crate::doc::cmake_parse::tests::{quoted_token, token, tokens_vec};
54    use crate::*;
55    use pretty_assertions::assert_eq;
56
57    #[test]
58    fn target_sources() {
59        let src = include_bytes!("../../../../../fixture/commands/project/target_sources");
60        let cmakelists = parse_cmakelists(src).unwrap();
61        let doc = Doc::from(cmakelists);
62        assert_eq!(
63            doc.commands(),
64            Ok(vec![
65                Command::TargetSources(Box::new(TargetSources {
66                    target: token(b"MyTarget"),
67                    sources: vec![Source::Private(vec![SourceItem::Item(quoted_token(
68                        b"$<$<CONFIG:Debug>:${CMAKE_CURRENT_SOURCE_DIR}/dbgsrc.cpp>"
69                    ))])]
70                })),
71                Command::TargetSources(Box::new(TargetSources {
72                    target: token(b"${targetNameTests}"),
73                    sources: vec![
74                        Source::Private(vec![
75                            SourceItem::Item(token(b"${ADD_TEST_TARGET_MAINFILE}")),
76                            SourceItem::Item(token(b"${ADD_TEST_TARGET_PRIVATEFILES}")),
77                            SourceItem::Item(token(b"${ADD_TEST_TARGET_TESTFILES}")),
78                        ]),
79                        Source::Public(vec![
80                            SourceItem::Item(token(b"${ADD_TEST_TARGET_PUBLICFILES}")),
81                            SourceItem::FileSet(FileSet {
82                                file_set: token(b"${targetNameTests}_cxx_modules"),
83                                file_set_type: Some(token(b"CXX_MODULES")),
84                                base_dirs: None,
85                                files: Some(tokens_vec([b"${ADD_TEST_TARGET_MODULEFILES}"]))
86                            }),
87                        ]),
88                        Source::Interface(vec![SourceItem::Item(token(
89                            b"${ADD_TEST_TARGET_INTERFACEFILES}"
90                        )),])
91                    ]
92                })),
93            ])
94        )
95    }
96}