guppy/graph/
mod.rs
1use crate::PackageId;
10use petgraph::prelude::*;
11use std::fmt;
12
13mod build;
14mod build_targets;
15pub mod cargo;
16mod cycles;
17pub mod feature;
18mod graph_impl;
19#[cfg(feature = "proptest1")]
20mod proptest_helpers;
21mod query;
22mod query_core;
23mod resolve;
24mod resolve_core;
25#[cfg(feature = "summaries")]
26pub mod summaries;
27
28pub use crate::petgraph_support::dot::DotWrite;
29pub use build_targets::*;
30pub use cycles::*;
31pub use graph_impl::*;
32use once_cell::sync::Lazy;
33use petgraph::graph::IndexType;
34#[cfg(feature = "proptest1")]
35pub use proptest_helpers::*;
36pub use query::*;
37pub use resolve::*;
38use semver::{Version, VersionReq};
39
40#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq)]
44#[cfg_attr(feature = "proptest1", derive(proptest_derive::Arbitrary))]
45pub enum DependencyDirection {
46 Forward,
48 Reverse,
50}
51
52impl DependencyDirection {
53 pub fn opposite(self) -> Self {
55 match self {
56 DependencyDirection::Forward => DependencyDirection::Reverse,
57 DependencyDirection::Reverse => DependencyDirection::Forward,
58 }
59 }
60}
61
62impl From<Direction> for DependencyDirection {
63 fn from(direction: Direction) -> Self {
64 match direction {
65 Direction::Outgoing => DependencyDirection::Forward,
66 Direction::Incoming => DependencyDirection::Reverse,
67 }
68 }
69}
70
71impl From<DependencyDirection> for Direction {
72 fn from(direction: DependencyDirection) -> Self {
73 match direction {
74 DependencyDirection::Forward => Direction::Outgoing,
75 DependencyDirection::Reverse => Direction::Incoming,
76 }
77 }
78}
79
80#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
82struct PackageIx(u32);
83
84#[derive(Clone, Copy, Debug, Default, Eq, Hash, Ord, PartialEq, PartialOrd)]
86struct FeatureIx(u32);
87
88macro_rules! graph_ix {
89 ($ix_type: ident) => {
90 impl fmt::Display for $ix_type {
91 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
92 write!(f, "{}", self.0)
93 }
94 }
95
96 unsafe impl IndexType for $ix_type {
100 #[inline(always)]
101 fn new(x: usize) -> Self {
102 $ix_type(x as u32)
103 }
104 #[inline(always)]
105 fn index(&self) -> usize {
106 self.0 as usize
107 }
108 #[inline(always)]
109 fn max() -> Self {
110 $ix_type(u32::MAX)
111 }
112 }
113 };
114}
115
116graph_ix!(PackageIx);
117graph_ix!(FeatureIx);
118
119trait GraphSpec {
121 type Node;
122 type Edge;
123 type Ix: IndexType;
124}
125
126impl GraphSpec for PackageGraph {
127 type Node = PackageId;
128 type Edge = PackageLinkImpl;
129 type Ix = PackageIx;
130}
131
132#[derive(Clone, Debug)]
137pub(crate) enum FeatureGraphSpec {}
138
139impl GraphSpec for FeatureGraphSpec {
140 type Node = feature::FeatureNode;
141 type Edge = feature::FeatureEdge;
142 type Ix = FeatureIx;
143}
144
145fn cargo_version_matches(req: &VersionReq, version: &Version) -> bool {
149 static MAJOR_WILDCARD: Lazy<VersionReq> = Lazy::new(|| VersionReq::parse("*").unwrap());
150
151 req == &*MAJOR_WILDCARD || req.matches(version)
152}