@@ -11,6 +11,7 @@ export interface GraphDependency {
1111interface DependencyNode extends d3 . SimulationNodeDatum {
1212 id : string ;
1313 color : string ;
14+ cve_count : number ;
1415}
1516
1617interface DependencyLink extends d3 . SimulationLinkDatum < DependencyNode > {
@@ -60,11 +61,11 @@ const DependencyGraph: React.FC = () => {
6061 svg . append ( 'defs' ) . append ( 'marker' )
6162 . attr ( 'id' , 'arrowhead' )
6263 . attr ( 'viewBox' , '0 -5 10 10' )
63- . attr ( 'refX' , 17 )
64+ . attr ( 'refX' , 8 )
6465 . attr ( 'refY' , 0 )
6566 . attr ( 'orient' , 'auto' )
66- . attr ( 'markerWidth' , 3 )
67- . attr ( 'markerHeight' , 3 )
67+ . attr ( 'markerWidth' , 6 )
68+ . attr ( 'markerHeight' , 6 )
6869 . append ( 'path' )
6970 . attr ( 'd' , 'M 0,-5 L 10,0 L 0,5' )
7071 . attr ( 'fill' , '#333' )
@@ -77,7 +78,21 @@ const DependencyGraph: React.FC = () => {
7778 const nodeId = `${ dep . name_and_version } ` ;
7879 let node = nodesMap . get ( nodeId ) ;
7980 if ( ! node ) {
80- node = { id : nodeId , color : parent ? '#5c6470' : '#32e0c4' } ;
81+ const getColorByCveCount = ( count : number ) => {
82+ if ( count === 0 ) return '#2ecc71' ; // 绿色
83+ if ( count >= 10 ) return '#8b0000' ; // 深红色
84+ if ( count >= 6 ) return '#e74c3c' ; // 红色
85+ if ( count >= 3 ) return '#e67e22' ; // 橙色
86+ if ( count >= 1 ) return '#f1c40f' ; // 黄色
87+ return '#2ecc71' ; // 默认绿色
88+ } ;
89+
90+ const nodeColor = ! parent ? '#32e0c4' : getColorByCveCount ( dep . cve_count ) ;
91+ node = {
92+ id : nodeId ,
93+ color : nodeColor ,
94+ cve_count : dep . cve_count
95+ } ;
8196 nodesMap . set ( nodeId , node ) ;
8297 }
8398 if ( parent ) {
@@ -96,7 +111,7 @@ const DependencyGraph: React.FC = () => {
96111 . force ( 'link' , d3 . forceLink < DependencyNode , DependencyLink > ( links ) . id ( d => d . id ) . distance ( 80 ) )
97112 . force ( 'charge' , d3 . forceManyBody ( ) . strength ( - 300 ) )
98113 . force ( 'center' , d3 . forceCenter ( width / 2 , height / 2 ) )
99- . force ( 'collide' , d3 . forceCollide ( ) . radius ( 10 ) ) ;
114+ . force ( 'collide' , d3 . forceCollide ( ) . radius ( 15 ) ) ;
100115
101116 const g = svg . append ( 'g' ) ;
102117
@@ -106,13 +121,25 @@ const DependencyGraph: React.FC = () => {
106121 . enter ( ) . append ( 'line' )
107122 . attr ( 'stroke-width' , 1.5 )
108123 . attr ( 'stroke' , '#333' )
109- . attr ( 'marker-end' , 'url(#arrowhead)' ) ;
124+ . attr ( 'marker-end' , 'url(#arrowhead)' )
125+ . attr ( 'x2' , function ( d ) {
126+ const dx = ( d . target as DependencyNode ) . x ! - ( d . source as DependencyNode ) . x ! ;
127+ const dy = ( d . target as DependencyNode ) . y ! - ( d . source as DependencyNode ) . y ! ;
128+ const dist = Math . sqrt ( dx * dx + dy * dy ) ;
129+ return dist === 0 ? 0 : ( d . target as DependencyNode ) . x ! - ( dx * 15 / dist ) ;
130+ } )
131+ . attr ( 'y2' , function ( d ) {
132+ const dx = ( d . target as DependencyNode ) . x ! - ( d . source as DependencyNode ) . x ! ;
133+ const dy = ( d . target as DependencyNode ) . y ! - ( d . source as DependencyNode ) . y ! ;
134+ const dist = Math . sqrt ( dx * dx + dy * dy ) ;
135+ return dist === 0 ? 0 : ( d . target as DependencyNode ) . y ! - ( dy * 15 / dist ) ;
136+ } ) ;
110137
111138 const node = g . append ( 'g' )
112139 . selectAll ( 'circle' )
113140 . data ( nodes )
114141 . enter ( ) . append ( 'circle' )
115- . attr ( 'r' , 5 )
142+ . attr ( 'r' , 8 )
116143 . attr ( 'fill' , d => d . color )
117144 . attr ( 'stroke' , '#333' )
118145 . attr ( 'stroke-width' , 1.5 )
@@ -144,8 +171,18 @@ const DependencyGraph: React.FC = () => {
144171 link
145172 . attr ( 'x1' , d => ( d . source as DependencyNode ) . x ! )
146173 . attr ( 'y1' , d => ( d . source as DependencyNode ) . y ! )
147- . attr ( 'x2' , d => ( d . target as DependencyNode ) . x ! )
148- . attr ( 'y2' , d => ( d . target as DependencyNode ) . y ! ) ;
174+ . attr ( 'x2' , function ( d ) {
175+ const dx = ( d . target as DependencyNode ) . x ! - ( d . source as DependencyNode ) . x ! ;
176+ const dy = ( d . target as DependencyNode ) . y ! - ( d . source as DependencyNode ) . y ! ;
177+ const dist = Math . sqrt ( dx * dx + dy * dy ) ;
178+ return dist === 0 ? 0 : ( d . target as DependencyNode ) . x ! - ( dx * 15 / dist ) ;
179+ } )
180+ . attr ( 'y2' , function ( d ) {
181+ const dx = ( d . target as DependencyNode ) . x ! - ( d . source as DependencyNode ) . x ! ;
182+ const dy = ( d . target as DependencyNode ) . y ! - ( d . source as DependencyNode ) . y ! ;
183+ const dist = Math . sqrt ( dx * dx + dy * dy ) ;
184+ return dist === 0 ? 0 : ( d . target as DependencyNode ) . y ! - ( dy * 15 / dist ) ;
185+ } ) ;
149186
150187 node
151188 . attr ( 'cx' , d => d . x ! )
0 commit comments