risk-network 0.0.6b3__py3-none-any.whl → 0.0.6b4__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- risk/__init__.py +1 -1
- risk/annotations/io.py +29 -0
- risk/neighborhoods/domains.py +24 -18
- risk/network/graph.py +13 -9
- risk/network/plot.py +51 -23
- {risk_network-0.0.6b3.dist-info → risk_network-0.0.6b4.dist-info}/METADATA +1 -1
- {risk_network-0.0.6b3.dist-info → risk_network-0.0.6b4.dist-info}/RECORD +10 -10
- {risk_network-0.0.6b3.dist-info → risk_network-0.0.6b4.dist-info}/LICENSE +0 -0
- {risk_network-0.0.6b3.dist-info → risk_network-0.0.6b4.dist-info}/WHEEL +0 -0
- {risk_network-0.0.6b3.dist-info → risk_network-0.0.6b4.dist-info}/top_level.txt +0 -0
risk/__init__.py
CHANGED
risk/annotations/io.py
CHANGED
@@ -153,6 +153,35 @@ class AnnotationsIO:
|
|
153
153
|
# Load the annotations into the provided network
|
154
154
|
return load_annotations(network, annotations_input)
|
155
155
|
|
156
|
+
def load_dict_annotation(self, content: Dict[str, Any], network: nx.Graph) -> Dict[str, Any]:
|
157
|
+
"""Load annotations from a provided dictionary and convert them to a dictionary annotation.
|
158
|
+
|
159
|
+
Args:
|
160
|
+
content (dict): The annotations dictionary to load.
|
161
|
+
network (NetworkX graph): The network to which the annotations are related.
|
162
|
+
|
163
|
+
Returns:
|
164
|
+
dict: A dictionary containing ordered nodes, ordered annotations, and the annotations matrix.
|
165
|
+
"""
|
166
|
+
# Ensure the input content is a dictionary
|
167
|
+
if not isinstance(content, dict):
|
168
|
+
raise TypeError(
|
169
|
+
f"Expected 'content' to be a dictionary, but got {type(content).__name__} instead."
|
170
|
+
)
|
171
|
+
|
172
|
+
filetype = "Dictionary"
|
173
|
+
# Log the loading of the annotations from the dictionary
|
174
|
+
params.log_annotations(filepath="In-memory dictionary", filetype=filetype)
|
175
|
+
_log_loading(filetype, "In-memory dictionary")
|
176
|
+
|
177
|
+
# Load the annotations into the provided network
|
178
|
+
annotations_dict = load_annotations(network, content)
|
179
|
+
# Ensure the output is a dictionary
|
180
|
+
if not isinstance(annotations_dict, dict):
|
181
|
+
raise ValueError("Expected output to be a dictionary")
|
182
|
+
|
183
|
+
return annotations_dict
|
184
|
+
|
156
185
|
|
157
186
|
def _load_matrix_file(
|
158
187
|
filepath: str,
|
risk/neighborhoods/domains.py
CHANGED
@@ -35,26 +35,31 @@ def define_domains(
|
|
35
35
|
Returns:
|
36
36
|
pd.DataFrame: DataFrame with the primary domain for each node.
|
37
37
|
"""
|
38
|
-
#
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
38
|
+
# Check if there's more than one column in significant_neighborhoods_enrichment
|
39
|
+
if significant_neighborhoods_enrichment.shape[1] == 1:
|
40
|
+
print("Single annotation detected. Skipping clustering.")
|
41
|
+
top_annotations["domain"] = 1 # Assign a default domain or handle appropriately
|
42
|
+
else:
|
43
|
+
# Perform hierarchical clustering on the binary enrichment matrix
|
44
|
+
m = significant_neighborhoods_enrichment[:, top_annotations["top attributes"]].T
|
45
|
+
best_linkage, best_metric, best_threshold = _optimize_silhouette_across_linkage_and_metrics(
|
46
|
+
m, linkage_criterion, linkage_method, linkage_metric
|
47
|
+
)
|
48
|
+
try:
|
49
|
+
Z = linkage(m, method=best_linkage, metric=best_metric)
|
50
|
+
except ValueError as e:
|
51
|
+
raise ValueError("No significant annotations found.") from e
|
47
52
|
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
53
|
+
print(
|
54
|
+
f"Linkage criterion: '{linkage_criterion}'\nLinkage method: '{best_linkage}'\nLinkage metric: '{best_metric}'"
|
55
|
+
)
|
56
|
+
print(f"Optimal linkage threshold: {round(best_threshold, 3)}")
|
52
57
|
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
+
max_d_optimal = np.max(Z[:, 2]) * best_threshold
|
59
|
+
domains = fcluster(Z, max_d_optimal, criterion=linkage_criterion)
|
60
|
+
# Assign domains to the annotations matrix
|
61
|
+
top_annotations["domain"] = 0
|
62
|
+
top_annotations.loc[top_annotations["top attributes"], "domain"] = domains
|
58
63
|
|
59
64
|
# Create DataFrames to store domain information
|
60
65
|
node_to_enrichment = pd.DataFrame(
|
@@ -63,6 +68,7 @@ def define_domains(
|
|
63
68
|
)
|
64
69
|
node_to_domain = node_to_enrichment.groupby(level="domain", axis=1).sum()
|
65
70
|
|
71
|
+
# Find the maximum enrichment score for each node
|
66
72
|
t_max = node_to_domain.loc[:, 1:].max(axis=1)
|
67
73
|
t_idxmax = node_to_domain.loc[:, 1:].idxmax(axis=1)
|
68
74
|
t_idxmax[t_max == 0] = 0
|
risk/network/graph.py
CHANGED
@@ -42,12 +42,16 @@ class NetworkGraph:
|
|
42
42
|
node_enrichment_sums (np.ndarray): Array containing the enrichment sums for the nodes.
|
43
43
|
"""
|
44
44
|
self.top_annotations = top_annotations
|
45
|
-
self.
|
45
|
+
self.domain_to_nodes_map = self._create_domain_to_nodes_map(domains)
|
46
46
|
self.domains = domains
|
47
47
|
self.trimmed_domain_to_term = self._create_domain_to_term_map(trimmed_domains)
|
48
48
|
self.trimmed_domains = trimmed_domains
|
49
|
-
self.node_label_to_id_map = node_label_to_id_map
|
50
49
|
self.node_enrichment_sums = node_enrichment_sums
|
50
|
+
self.node_id_to_label_map = {v: k for k, v in node_label_to_id_map.items()}
|
51
|
+
self.node_label_to_enrichment_map = dict(
|
52
|
+
zip(node_label_to_id_map.keys(), node_enrichment_sums)
|
53
|
+
)
|
54
|
+
self.node_label_to_id_map = node_label_to_id_map
|
51
55
|
# NOTE: self.network and self.node_coordinates are declared in _initialize_network
|
52
56
|
self.network = None
|
53
57
|
self.node_coordinates = None
|
@@ -63,12 +67,12 @@ class NetworkGraph:
|
|
63
67
|
dict: A dictionary where keys are domain IDs and values are lists of nodes belonging to each domain.
|
64
68
|
"""
|
65
69
|
cleaned_domains_matrix = domains.reset_index()[["index", "primary domain"]]
|
66
|
-
|
67
|
-
|
68
|
-
for k, v in
|
69
|
-
|
70
|
+
node_to_domains_map = cleaned_domains_matrix.set_index("index")["primary domain"].to_dict()
|
71
|
+
domain_to_nodes_map = defaultdict(list)
|
72
|
+
for k, v in node_to_domains_map.items():
|
73
|
+
domain_to_nodes_map[v].append(k)
|
70
74
|
|
71
|
-
return
|
75
|
+
return domain_to_nodes_map
|
72
76
|
|
73
77
|
def _create_domain_to_term_map(self, trimmed_domains: pd.DataFrame) -> Dict[str, Any]:
|
74
78
|
"""Create a mapping from domain IDs to their corresponding terms.
|
@@ -154,7 +158,7 @@ class NetworkGraph:
|
|
154
158
|
# Initialize composite colors array with shape (number of nodes, 4) for RGBA
|
155
159
|
composite_colors = np.zeros((num_nodes, 4))
|
156
160
|
# Assign colors to nodes based on domain_colors
|
157
|
-
for domain_idx, nodes in self.
|
161
|
+
for domain_idx, nodes in self.domain_to_nodes_map.items():
|
158
162
|
color = domain_colors[domain_idx]
|
159
163
|
for node in nodes:
|
160
164
|
composite_colors[node] = color
|
@@ -185,7 +189,7 @@ class NetworkGraph:
|
|
185
189
|
domain_colors = _get_colors(
|
186
190
|
num_colors_to_generate=len(domains), cmap=cmap, color=color, random_seed=random_seed
|
187
191
|
)
|
188
|
-
return dict(zip(self.
|
192
|
+
return dict(zip(self.domain_to_nodes_map.keys(), domain_colors))
|
189
193
|
|
190
194
|
|
191
195
|
def _transform_colors(
|
risk/network/plot.py
CHANGED
@@ -279,6 +279,7 @@ class NetworkPlotter:
|
|
279
279
|
nodes: List,
|
280
280
|
node_size: Union[int, np.ndarray] = 50,
|
281
281
|
node_shape: str = "o",
|
282
|
+
node_edgewidth: float = 1.0, # Added node_edgewidth parameter
|
282
283
|
edge_width: float = 1.0,
|
283
284
|
node_color: Union[str, List, Tuple, np.ndarray] = "white",
|
284
285
|
node_edgecolor: Union[str, List, Tuple, np.ndarray] = "black",
|
@@ -292,6 +293,7 @@ class NetworkPlotter:
|
|
292
293
|
nodes (list): List of node labels to include in the subnetwork.
|
293
294
|
node_size (int or np.ndarray, optional): Size of the nodes. Can be a single integer or an array of sizes. Defaults to 50.
|
294
295
|
node_shape (str, optional): Shape of the nodes. Defaults to "o".
|
296
|
+
node_edgewidth (float, optional): Width of the node edges. Defaults to 1.0.
|
295
297
|
edge_width (float, optional): Width of the edges. Defaults to 1.0.
|
296
298
|
node_color (str, list, tuple, or np.ndarray, optional): Color of the nodes. Can be a single color or an array of colors. Defaults to "white".
|
297
299
|
node_edgecolor (str, list, tuple, or np.ndarray, optional): Color of the node edges. Defaults to "black".
|
@@ -302,7 +304,6 @@ class NetworkPlotter:
|
|
302
304
|
Raises:
|
303
305
|
ValueError: If no valid nodes are found in the network graph.
|
304
306
|
"""
|
305
|
-
# Don't log subnetwork parameters as they are specific to individual annotations
|
306
307
|
# Filter to get node IDs and their coordinates
|
307
308
|
node_ids = [
|
308
309
|
self.graph.node_label_to_id_map.get(node)
|
@@ -312,10 +313,18 @@ class NetworkPlotter:
|
|
312
313
|
if not node_ids:
|
313
314
|
raise ValueError("No nodes found in the network graph.")
|
314
315
|
|
316
|
+
# If node_color is an array, match its length to the found node_ids
|
317
|
+
if not isinstance(node_color, str):
|
318
|
+
node_color = [
|
319
|
+
node_color[nodes.index(node)]
|
320
|
+
for node in nodes
|
321
|
+
if node in self.graph.node_label_to_id_map
|
322
|
+
]
|
323
|
+
|
315
324
|
# Convert colors to RGBA using the _to_rgba helper function
|
316
|
-
node_color = _to_rgba(node_color, node_alpha)
|
317
|
-
node_edgecolor = _to_rgba(node_edgecolor, 1.0)
|
318
|
-
edge_color = _to_rgba(edge_color, edge_alpha)
|
325
|
+
node_color = _to_rgba(node_color, node_alpha, num_repeats=len(node_ids))
|
326
|
+
node_edgecolor = _to_rgba(node_edgecolor, 1.0, num_repeats=len(node_ids))
|
327
|
+
edge_color = _to_rgba(edge_color, edge_alpha, num_repeats=len(self.graph.network.edges))
|
319
328
|
# Get the coordinates of the filtered nodes
|
320
329
|
node_coordinates = {node_id: self.graph.node_coordinates[node_id] for node_id in node_ids}
|
321
330
|
|
@@ -328,6 +337,7 @@ class NetworkPlotter:
|
|
328
337
|
node_shape=node_shape,
|
329
338
|
node_color=node_color,
|
330
339
|
edgecolors=node_edgecolor,
|
340
|
+
linewidths=node_edgewidth,
|
331
341
|
ax=self.ax,
|
332
342
|
)
|
333
343
|
# Draw the edges between the specified nodes in the subnetwork
|
@@ -373,11 +383,11 @@ class NetworkPlotter:
|
|
373
383
|
)
|
374
384
|
|
375
385
|
# Ensure color is converted to RGBA with repetition matching the number of domains
|
376
|
-
color = _to_rgba(color, alpha, num_repeats=len(self.graph.
|
386
|
+
color = _to_rgba(color, alpha, num_repeats=len(self.graph.domain_to_nodes_map))
|
377
387
|
# Extract node coordinates from the network graph
|
378
388
|
node_coordinates = self.graph.node_coordinates
|
379
389
|
# Draw contours for each domain in the network
|
380
|
-
for idx, (_, nodes) in enumerate(self.graph.
|
390
|
+
for idx, (_, nodes) in enumerate(self.graph.domain_to_nodes_map.items()):
|
381
391
|
if len(nodes) > 1:
|
382
392
|
self._draw_kde_contour(
|
383
393
|
self.ax,
|
@@ -580,9 +590,9 @@ class NetworkPlotter:
|
|
580
590
|
)
|
581
591
|
|
582
592
|
# Convert colors to RGBA using the _to_rgba helper function, applying alpha separately for font and arrow
|
583
|
-
fontcolor = _to_rgba(fontcolor, fontalpha, num_repeats=len(self.graph.
|
593
|
+
fontcolor = _to_rgba(fontcolor, fontalpha, num_repeats=len(self.graph.domain_to_nodes_map))
|
584
594
|
arrow_color = _to_rgba(
|
585
|
-
arrow_color, arrow_alpha, num_repeats=len(self.graph.
|
595
|
+
arrow_color, arrow_alpha, num_repeats=len(self.graph.domain_to_nodes_map)
|
586
596
|
)
|
587
597
|
|
588
598
|
# Normalize words_to_omit to lowercase
|
@@ -591,7 +601,7 @@ class NetworkPlotter:
|
|
591
601
|
|
592
602
|
# Calculate the center and radius of the network
|
593
603
|
domain_centroids = {}
|
594
|
-
for domain, nodes in self.graph.
|
604
|
+
for domain, nodes in self.graph.domain_to_nodes_map.items():
|
595
605
|
if nodes: # Skip if the domain has no nodes
|
596
606
|
domain_centroids[domain] = self._calculate_domain_centroid(nodes)
|
597
607
|
|
@@ -811,9 +821,9 @@ class NetworkPlotter:
|
|
811
821
|
Returns:
|
812
822
|
np.ndarray: Array of node sizes, with enriched nodes larger than non-enriched ones.
|
813
823
|
"""
|
814
|
-
# Merge all enriched nodes from the
|
824
|
+
# Merge all enriched nodes from the domain_to_nodes_map dictionary
|
815
825
|
enriched_nodes = set()
|
816
|
-
for _, nodes in self.graph.
|
826
|
+
for _, nodes in self.graph.domain_to_nodes_map.items():
|
817
827
|
enriched_nodes.update(nodes)
|
818
828
|
|
819
829
|
# Initialize all node sizes to the non-enriched size
|
@@ -928,7 +938,7 @@ class NetworkPlotter:
|
|
928
938
|
random_seed=random_seed,
|
929
939
|
)
|
930
940
|
annotated_colors = []
|
931
|
-
for _, nodes in self.graph.
|
941
|
+
for _, nodes in self.graph.domain_to_nodes_map.items():
|
932
942
|
if len(nodes) > 1:
|
933
943
|
# For multi-node domains, choose the brightest color based on RGB sum
|
934
944
|
domain_colors = np.array([node_colors[node] for node in nodes])
|
@@ -969,33 +979,51 @@ def _to_rgba(
|
|
969
979
|
alpha: float = 1.0,
|
970
980
|
num_repeats: Union[int, None] = None,
|
971
981
|
) -> np.ndarray:
|
972
|
-
"""Convert a color or array of colors to RGBA format, applying
|
982
|
+
"""Convert a color or array of colors to RGBA format, applying alpha only if the color is RGB.
|
973
983
|
|
974
984
|
Args:
|
975
985
|
color (Union[str, list, tuple, np.ndarray]): The color(s) to convert. Can be a string, list, tuple, or np.ndarray.
|
976
|
-
alpha (float, optional): Alpha value (transparency) to apply. Defaults to 1.0.
|
986
|
+
alpha (float, optional): Alpha value (transparency) to apply if the color is in RGB format. Defaults to 1.0.
|
977
987
|
num_repeats (int or None, optional): If provided, the color will be repeated this many times. Defaults to None.
|
978
988
|
|
979
989
|
Returns:
|
980
990
|
np.ndarray: The RGBA color or array of RGBA colors.
|
981
991
|
"""
|
982
|
-
# Handle single color case
|
992
|
+
# Handle single color case (string, RGB, or RGBA)
|
983
993
|
if isinstance(color, str) or (
|
984
994
|
isinstance(color, (list, tuple, np.ndarray)) and len(color) in [3, 4]
|
985
995
|
):
|
986
|
-
rgba_color = np.array(mcolors.to_rgba(color
|
987
|
-
#
|
996
|
+
rgba_color = np.array(mcolors.to_rgba(color))
|
997
|
+
# Only set alpha if the input is an RGB color or a string (not RGBA)
|
998
|
+
if len(rgba_color) == 4 and (
|
999
|
+
len(color) == 3 or isinstance(color, str)
|
1000
|
+
): # If it's RGB or a string, set the alpha
|
1001
|
+
rgba_color[3] = alpha
|
1002
|
+
|
1003
|
+
# Repeat the color if num_repeats argument is provided
|
988
1004
|
if num_repeats is not None:
|
989
1005
|
return np.array([rgba_color] * num_repeats)
|
990
1006
|
|
991
1007
|
return rgba_color
|
992
1008
|
|
993
|
-
# Handle array of colors case
|
994
|
-
elif isinstance(color, (list, tuple, np.ndarray))
|
995
|
-
|
996
|
-
|
997
|
-
|
998
|
-
|
1009
|
+
# Handle array of colors case (including strings, RGB, and RGBA)
|
1010
|
+
elif isinstance(color, (list, tuple, np.ndarray)):
|
1011
|
+
rgba_colors = []
|
1012
|
+
for c in color:
|
1013
|
+
# Ensure each element is either a valid string or a list/tuple of length 3 (RGB) or 4 (RGBA)
|
1014
|
+
if isinstance(c, str) or (
|
1015
|
+
isinstance(c, (list, tuple, np.ndarray)) and len(c) in [3, 4]
|
1016
|
+
):
|
1017
|
+
rgba_c = np.array(mcolors.to_rgba(c))
|
1018
|
+
# Apply alpha only to RGB colors (not RGBA) and strings
|
1019
|
+
if len(rgba_c) == 4 and (len(c) == 3 or isinstance(c, str)):
|
1020
|
+
rgba_c[3] = alpha
|
1021
|
+
|
1022
|
+
rgba_colors.append(rgba_c)
|
1023
|
+
else:
|
1024
|
+
raise ValueError(f"Invalid color: {c}. Must be a valid RGB/RGBA or string color.")
|
1025
|
+
|
1026
|
+
# Repeat the colors if num_repeats argument is provided
|
999
1027
|
if num_repeats is not None and len(rgba_colors) == 1:
|
1000
1028
|
return np.array([rgba_colors[0]] * num_repeats)
|
1001
1029
|
|
@@ -1,21 +1,21 @@
|
|
1
|
-
risk/__init__.py,sha256=
|
1
|
+
risk/__init__.py,sha256=AGEvxxDrf1pHNa6sursCylT1nkxBgi_16zOuGB4SYbk,112
|
2
2
|
risk/constants.py,sha256=XInRaH78Slnw_sWgAsBFbUHkyA0h0jL0DKGuQNbOvjM,550
|
3
3
|
risk/risk.py,sha256=PONl5tzN5DSVUf4MgczfOvzGV-5JoAOLTQ6YWl10mZ8,20697
|
4
4
|
risk/annotations/__init__.py,sha256=vUpVvMRE5if01Ic8QY6M2Ae3EFGJHdugEe9PdEkAW4Y,138
|
5
5
|
risk/annotations/annotations.py,sha256=DRUTdGzMdqo62NWSapBUksbvPr9CrzD76qtOcxeNKmo,10554
|
6
|
-
risk/annotations/io.py,sha256=
|
6
|
+
risk/annotations/io.py,sha256=lo7NKqOVkeeBp58JBxWJHtA0xjL5Yoxqe9Ox0daKlZk,9457
|
7
7
|
risk/log/__init__.py,sha256=xuLImfxFlKpnVhzi_gDYlr2_c9cLkrw2c_3iEsXb1as,107
|
8
8
|
risk/log/console.py,sha256=im9DRExwf6wHlcn9fewoDcKIpo3vPcorZIaNAl-0csY,355
|
9
9
|
risk/log/params.py,sha256=Tbb-sovFTptGBqPDKafUA8KOpby4zFObutAT_Iti1hE,6302
|
10
10
|
risk/neighborhoods/__init__.py,sha256=tKKEg4lsbqFukpgYlUGxU_v_9FOqK7V0uvM9T2QzoL0,206
|
11
11
|
risk/neighborhoods/community.py,sha256=7ebo1Q5KokSQISnxZIh2SQxsKXdXm8aVkp-h_DiQ3K0,6818
|
12
|
-
risk/neighborhoods/domains.py,sha256=
|
12
|
+
risk/neighborhoods/domains.py,sha256=5V--Nj-TrSdubhD_2PI57ffcn_PMSEgpX_iY5OjT6R8,10626
|
13
13
|
risk/neighborhoods/neighborhoods.py,sha256=sHmjFFl2U5qV9YbQCRbpbI36j7dS7IFfFwwRb1_-AuM,13945
|
14
14
|
risk/network/__init__.py,sha256=iEPeJdZfqp0toxtbElryB8jbz9_t_k4QQ3iDvKE8C_0,126
|
15
15
|
risk/network/geometry.py,sha256=H1yGVVqgbfpzBzJwEheDLfvGLSA284jGQQTn612L4Vc,6759
|
16
|
-
risk/network/graph.py,sha256=
|
16
|
+
risk/network/graph.py,sha256=scPFQIJjioup1FjQLyxNrAB17RmskY9MmvoFHrMlqNI,13135
|
17
17
|
risk/network/io.py,sha256=gG50kOknO-D3HkW1HsbHMkTMvjUtn3l4W4Jwd-rXNr8,21202
|
18
|
-
risk/network/plot.py,sha256=
|
18
|
+
risk/network/plot.py,sha256=GjNZizcsJf6zjkEkvZv9LA456YmKbC2MO51AIzV5QOw,55342
|
19
19
|
risk/stats/__init__.py,sha256=e-BE_Dr_jgiK6hKM-T-tlG4yvHnId8e5qjnM0pdwNVc,230
|
20
20
|
risk/stats/fisher_exact.py,sha256=-bPwzu76-ob0HzrTV20mXUTot7v-MLuqFaAoab-QxPg,4966
|
21
21
|
risk/stats/hypergeom.py,sha256=lrIFdhCWRjvM4apYw1MlOKqT_IY5OjtCwrjdtJdt6Tg,4954
|
@@ -23,8 +23,8 @@ risk/stats/stats.py,sha256=kvShov-94W6ffgDUTb522vB9hDJQSyTsYif_UIaFfSM,7059
|
|
23
23
|
risk/stats/permutation/__init__.py,sha256=neJp7FENC-zg_CGOXqv-iIvz1r5XUKI9Ruxhmq7kDOI,105
|
24
24
|
risk/stats/permutation/permutation.py,sha256=qLWdwxEY6nmkYPxpM8HLDcd2mbqYv9Qr7CKtJvhLqIM,9220
|
25
25
|
risk/stats/permutation/test_functions.py,sha256=HuDIM-V1jkkfE1rlaIqrWWBSKZt3dQ1f-YEDjWpnLSE,2343
|
26
|
-
risk_network-0.0.
|
27
|
-
risk_network-0.0.
|
28
|
-
risk_network-0.0.
|
29
|
-
risk_network-0.0.
|
30
|
-
risk_network-0.0.
|
26
|
+
risk_network-0.0.6b4.dist-info/LICENSE,sha256=jOtLnuWt7d5Hsx6XXB2QxzrSe2sWWh3NgMfFRetluQM,35147
|
27
|
+
risk_network-0.0.6b4.dist-info/METADATA,sha256=MxZC6-0dLvPwBCCA5nL2NnnamuhaRA5uSmFK0o13DPU,43142
|
28
|
+
risk_network-0.0.6b4.dist-info/WHEEL,sha256=cVxcB9AmuTcXqmwrtPhNK88dr7IR_b6qagTj0UvIEbY,91
|
29
|
+
risk_network-0.0.6b4.dist-info/top_level.txt,sha256=NX7C2PFKTvC1JhVKv14DFlFAIFnKc6Lpsu1ZfxvQwVw,5
|
30
|
+
risk_network-0.0.6b4.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|