Fast-HInt-ppi 0.1.0__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.
- Fast_HInt/File_proteins.py +780 -0
- Fast_HInt/HInt.py +244 -0
- Fast_HInt/Scoring_HInt.py +954 -0
- Fast_HInt/Utils_HInt.py +1313 -0
- Fast_HInt/__init__.py +1 -0
- Fast_HInt/get_good_inter_pae.py +340 -0
- fast_hint_ppi-0.1.0.dist-info/METADATA +33 -0
- fast_hint_ppi-0.1.0.dist-info/RECORD +11 -0
- fast_hint_ppi-0.1.0.dist-info/WHEEL +5 -0
- fast_hint_ppi-0.1.0.dist-info/entry_points.txt +2 -0
- fast_hint_ppi-0.1.0.dist-info/top_level.txt +1 -0
Fast_HInt/HInt.py
ADDED
|
@@ -0,0 +1,244 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Main entry point of HInt
|
|
3
|
+
|
|
4
|
+
Author: Quentin Rouger
|
|
5
|
+
|
|
6
|
+
This script orchestrates the full HInt pipeline, from input parsing to final results generation.
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
import sys
|
|
10
|
+
import logging
|
|
11
|
+
import argparse
|
|
12
|
+
import os
|
|
13
|
+
import threading
|
|
14
|
+
|
|
15
|
+
# ------------------------------------------------------------------
|
|
16
|
+
# Logging configuration
|
|
17
|
+
# ------------------------------------------------------------------
|
|
18
|
+
|
|
19
|
+
log_filename = "./log_file/HInt.log"
|
|
20
|
+
|
|
21
|
+
# Create log directory if it does not exist
|
|
22
|
+
if not os.path.exists("log_file") :
|
|
23
|
+
os.system("mkdir log_file")
|
|
24
|
+
|
|
25
|
+
from .Utils_HInt import *
|
|
26
|
+
from .File_proteins import *
|
|
27
|
+
from .Scoring_HInt import Score_interaction, Resume_file, Create_figures
|
|
28
|
+
|
|
29
|
+
# Reset existing handlers to avoid duplicated logs
|
|
30
|
+
logging.getLogger().handlers.clear()
|
|
31
|
+
logger = logging.getLogger()
|
|
32
|
+
logger.setLevel(logging.INFO)
|
|
33
|
+
formatter = logging.Formatter("%(asctime)s - %(levelname)s - %(message)s")
|
|
34
|
+
file_handler = logging.FileHandler(log_filename, mode='w')
|
|
35
|
+
file_handler.setFormatter(formatter)
|
|
36
|
+
stream_handler = logging.StreamHandler(sys.stdout)
|
|
37
|
+
stream_handler.setFormatter(formatter)
|
|
38
|
+
logger.addHandler(file_handler)
|
|
39
|
+
logger.addHandler(stream_handler)
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
# ------------------------------------------------------------------
|
|
43
|
+
# Argument parsing
|
|
44
|
+
# ------------------------------------------------------------------
|
|
45
|
+
|
|
46
|
+
def add_arguments(parser) :
|
|
47
|
+
"""
|
|
48
|
+
Define command-line arguments.
|
|
49
|
+
|
|
50
|
+
Parameters
|
|
51
|
+
----------
|
|
52
|
+
parser : argparse.ArgumentParser
|
|
53
|
+
"""
|
|
54
|
+
parser.add_argument("--gpu", help="Comma-separated list of GPUs available for computation (default: 0)", required=False, default="0")
|
|
55
|
+
|
|
56
|
+
N_CPU = multiprocessing.cpu_count()
|
|
57
|
+
default_cpu = N_CPU // 2 # by default, use half of the available CPUs
|
|
58
|
+
parser.add_argument("--cpu", help="Number of CPUs available for computation (default: half of the CPUs)", required=False, default=default_cpu, type=int)
|
|
59
|
+
parser.add_argument("--multi_job_per_gpu", help="Allow multiple jobs to run on the same GPU if VRAM allows it (default: True)", required=False, default="True")
|
|
60
|
+
parser.add_argument("--multi_scoring", help="Score all models of each interactions (default: False)", required=False, default="False")
|
|
61
|
+
|
|
62
|
+
# ------------------------------------------------------------------
|
|
63
|
+
# Main execution
|
|
64
|
+
# ------------------------------------------------------------------
|
|
65
|
+
|
|
66
|
+
def main() :
|
|
67
|
+
|
|
68
|
+
parser = argparse.ArgumentParser()
|
|
69
|
+
add_arguments(parser)
|
|
70
|
+
args = parser.parse_args()
|
|
71
|
+
|
|
72
|
+
GPU = [gpu for gpu in args.gpu.split(",")]
|
|
73
|
+
CPU = args.cpu
|
|
74
|
+
if CPU > multiprocessing.cpu_count() :
|
|
75
|
+
raise ValueError(f"Number of CPUs specified ({CPU}) exceeds the number of available CPUs ({multiprocessing.cpu_count()}).")
|
|
76
|
+
multi_job_per_gpu = args.multi_job_per_gpu
|
|
77
|
+
if multi_job_per_gpu not in ["True", "False"] :
|
|
78
|
+
raise ValueError("Invalid value for --multi_job_per_gpu. Need True or False.")
|
|
79
|
+
multi_scoring = args.multi_scoring
|
|
80
|
+
if multi_scoring not in ["True", "False"] :
|
|
81
|
+
raise ValueError("Invalid value for --multi_scoring. Need True or False.")
|
|
82
|
+
Informations_dict = Define_informations()
|
|
83
|
+
|
|
84
|
+
# --------------------------------------------------------------
|
|
85
|
+
# Initialize protein container
|
|
86
|
+
# --------------------------------------------------------------
|
|
87
|
+
|
|
88
|
+
HInt_object = File_proteins(Informations_dict["Path_Uniprot_ID"], Informations_dict["Interact_with"], Informations_dict["AlphaFold"])
|
|
89
|
+
|
|
90
|
+
logger.info("GPUs set to: %s", GPU)
|
|
91
|
+
logger.info("Number of CPUs set to: %s", CPU)
|
|
92
|
+
|
|
93
|
+
|
|
94
|
+
|
|
95
|
+
for bait in Informations_dict["Interact_with"] : # Check that all bait proteins exist in the protein list
|
|
96
|
+
if bait not in HInt_object.get_proteins() and bait != "" :
|
|
97
|
+
raise Exception(f"Bait {bait} not found in the protein list {Informations_dict['Path_Uniprot_ID']}")
|
|
98
|
+
|
|
99
|
+
# --------------------------------------------------------------
|
|
100
|
+
# Checkpointing: determine which features need to be computed
|
|
101
|
+
# --------------------------------------------------------------
|
|
102
|
+
|
|
103
|
+
# need_msa also includes proteins that only require signal peptide information
|
|
104
|
+
need_msa, need_pkl, need_DeepLoc = HInt_object.check_save_dict(Informations_dict["Path_Pickle_Feature"])
|
|
105
|
+
|
|
106
|
+
# Remove bait proteins from the prey list
|
|
107
|
+
HInt_object.set_possible_prey([protein for protein in HInt_object.get_possible_prey() if protein not in Informations_dict["Interact_with"]])
|
|
108
|
+
|
|
109
|
+
# --------------------------------------------------------------
|
|
110
|
+
# Length-based filtering
|
|
111
|
+
# --------------------------------------------------------------
|
|
112
|
+
|
|
113
|
+
# Filter proteins based on sequence length
|
|
114
|
+
# (default: remove proteins shorter than 20 AA)
|
|
115
|
+
need_msa, need_pkl, need_DeepLoc = filter_lenght(HInt_object, Informations_dict, need_msa, need_pkl, need_DeepLoc)
|
|
116
|
+
|
|
117
|
+
# --------------------------------------------------------------
|
|
118
|
+
# DeepLoc filtering
|
|
119
|
+
# --------------------------------------------------------------
|
|
120
|
+
|
|
121
|
+
|
|
122
|
+
if Informations_dict["Organism"] == "None" :
|
|
123
|
+
HInt_object.set_proteins_sequence_no_SP(HInt_object.get_proteins_sequence_SP()) #don't remove signal peptide
|
|
124
|
+
need_DeepLoc = []
|
|
125
|
+
|
|
126
|
+
if len(need_DeepLoc) > 0 : # Run DeepLoc only for proteins without localization information
|
|
127
|
+
run_deeploc(HInt_object, Informations_dict["Organism"], need_DeepLoc, GPU)
|
|
128
|
+
|
|
129
|
+
|
|
130
|
+
if Informations_dict["DeepLoc"].split(",") != ["None"] : # Apply DeepLoc-based filtering if enabled
|
|
131
|
+
need_msa, need_pkl = filter_deeploc(HInt_object, Informations_dict, need_msa, need_pkl)
|
|
132
|
+
|
|
133
|
+
HInt_object.Make_save_dict() # Save DeepLoc results
|
|
134
|
+
|
|
135
|
+
# --------------------------------------------------------------
|
|
136
|
+
# Signal peptide processing
|
|
137
|
+
# --------------------------------------------------------------
|
|
138
|
+
|
|
139
|
+
need_SP = list()
|
|
140
|
+
for protein in need_msa :
|
|
141
|
+
if protein not in HInt_object.get_proteins_sequence_no_SP().keys() or protein not in HInt_object.get_prot_SP().keys() : #protein need MSA but can already have sequence without SP
|
|
142
|
+
need_SP.append(protein)
|
|
143
|
+
|
|
144
|
+
|
|
145
|
+
if Informations_dict["Organism"] == "None" : # Run SignalP only if the organism is specified
|
|
146
|
+
need_SP = []
|
|
147
|
+
if len(need_SP) > 0 : # Run SignalP for proteins without signal peptide annotation
|
|
148
|
+
need_msa = run_SP(HInt_object, Informations_dict, need_SP, need_msa)
|
|
149
|
+
|
|
150
|
+
need_msa = check_exist_MSA(HInt_object, Informations_dict, need_msa) # Check for existing MSA files after SignalP processing
|
|
151
|
+
HInt_object.Make_save_dict() # Save sequences without signal peptides
|
|
152
|
+
|
|
153
|
+
for bait in Informations_dict["Interact_with"] : # Adjust bait protein lengths if specific regions are defined
|
|
154
|
+
if Informations_dict["Regions"][bait] != "0-0" :
|
|
155
|
+
dict_lenght = HInt_object.get_lenght_prot()
|
|
156
|
+
start = int(Informations_dict["Regions"][bait].split("-")[0])
|
|
157
|
+
end = int(Informations_dict["Regions"][bait].split("-")[1])
|
|
158
|
+
dict_lenght[bait] = end - start + 1
|
|
159
|
+
HInt_object.set_lenght_prot(dict_lenght)
|
|
160
|
+
|
|
161
|
+
|
|
162
|
+
# Filter proteins based on signal peptide criteria
|
|
163
|
+
need_msa, need_pkl = filter_signalP(HInt_object, Informations_dict, need_msa, need_pkl)
|
|
164
|
+
|
|
165
|
+
HInt_object.Make_save_dict()
|
|
166
|
+
|
|
167
|
+
# --------------------------------------------------------------
|
|
168
|
+
# Feature generation (MSA + pickle files)
|
|
169
|
+
# --------------------------------------------------------------
|
|
170
|
+
|
|
171
|
+
|
|
172
|
+
#Create batch just for loop on
|
|
173
|
+
job_with_vram_length = Generate_scripts(HInt_object, Informations_dict, "PPI_int", bait)
|
|
174
|
+
first_need_msa = []
|
|
175
|
+
first_need_pkl = []
|
|
176
|
+
First_batch = Generate_first_batch(job_with_vram_length, GPU, multi_job_per_gpu) #correspond to the first batch of proteins to process, based on the number of available GPUs and CPUs
|
|
177
|
+
if First_batch != None :
|
|
178
|
+
First_batch[0].append(bait) #add bait to the first batch, to make sure it is processed first
|
|
179
|
+
for prot in First_batch[0] :
|
|
180
|
+
if prot in need_msa :
|
|
181
|
+
first_need_msa.append(prot)
|
|
182
|
+
need_msa.remove(prot)
|
|
183
|
+
if prot in need_pkl :
|
|
184
|
+
first_need_pkl.append(prot)
|
|
185
|
+
need_pkl.remove(prot)
|
|
186
|
+
|
|
187
|
+
create_feature(HInt_object, Informations_dict, GPU, CPU, first_need_msa, first_need_pkl)
|
|
188
|
+
|
|
189
|
+
HInt_object.Make_save_dict()
|
|
190
|
+
prio_list_MSA = prioritize_by_vram_fit(job_with_vram_length, GPU)
|
|
191
|
+
batch_MSA = []
|
|
192
|
+
if prio_list_MSA != [] :
|
|
193
|
+
prio_list_MSA.pop(0) #remove first batch
|
|
194
|
+
for batch in prio_list_MSA :
|
|
195
|
+
new_prio_list = []
|
|
196
|
+
for prot in batch :
|
|
197
|
+
if prot in need_msa :
|
|
198
|
+
new_prio_list.append(prot)
|
|
199
|
+
if prot in need_pkl :
|
|
200
|
+
new_prio_list.append(prot)
|
|
201
|
+
batch_MSA.append(new_prio_list)
|
|
202
|
+
|
|
203
|
+
if len(first_need_msa) > 0 :
|
|
204
|
+
logger.info("Generating MSA depth figures")
|
|
205
|
+
Make_all_MSA_coverage(HInt_object, Informations_dict["Path_Pickle_Feature"], Informations_dict["Interact_with"], first_need_msa)
|
|
206
|
+
if Informations_dict["Interact_with"] != [''] :
|
|
207
|
+
for bait in Informations_dict["Multimer_bait"] :
|
|
208
|
+
if HInt_object.get_compounds() != {} :
|
|
209
|
+
gpu_thread = threading.Thread(
|
|
210
|
+
target=Generate_3D_model, args=(HInt_object, CPU, multi_scoring, Informations_dict, "PPI_int", job_with_vram_length, GPU, multi_job_per_gpu))
|
|
211
|
+
gpu_thread.start()
|
|
212
|
+
for batch in batch_MSA :
|
|
213
|
+
create_feature(HInt_object, Informations_dict, GPU, CPU, batch, [])
|
|
214
|
+
gpu_thread.join()
|
|
215
|
+
else :
|
|
216
|
+
gpu_thread = threading.Thread(target=Generate_3D_model, args=(HInt_object, CPU, multi_scoring, Informations_dict, "PPI_int", job_with_vram_length, GPU, multi_job_per_gpu))
|
|
217
|
+
gpu_thread.start()
|
|
218
|
+
for batch in batch_MSA :
|
|
219
|
+
create_feature(HInt_object, Informations_dict, GPU, CPU, batch, [])
|
|
220
|
+
gpu_thread.join()
|
|
221
|
+
Score_interaction(HInt_object, Informations_dict, CPU, "PPI_int", "", multi_scoring, bait) #if score is not done in Generate_3D_model, do it here
|
|
222
|
+
HInt_object.Make_save_dict()
|
|
223
|
+
# --------------------------------------------------------------
|
|
224
|
+
# Homo-oligomer modeling
|
|
225
|
+
# --------------------------------------------------------------
|
|
226
|
+
|
|
227
|
+
if int(Informations_dict["Homo-oligomer"]) > 1 :
|
|
228
|
+
#job_with_vram_length = Generate_scripts(HInt_object, Informations_dict, "homo_int", "")
|
|
229
|
+
Generate_3D_model(Informations_dict, "homo_int", job_with_vram_length, GPU, multi_job_per_gpu)
|
|
230
|
+
|
|
231
|
+
|
|
232
|
+
|
|
233
|
+
# --------------------------------------------------------------
|
|
234
|
+
# Final summary and figures
|
|
235
|
+
# --------------------------------------------------------------
|
|
236
|
+
|
|
237
|
+
|
|
238
|
+
sorted_protein = Resume_file(HInt_object, Informations_dict)
|
|
239
|
+
|
|
240
|
+
if Informations_dict["Interact_with"] != [''] :
|
|
241
|
+
|
|
242
|
+
Create_figures(HInt_object, Informations_dict, Informations_dict["AlphaFold"], sorted_protein, CPU)
|
|
243
|
+
|
|
244
|
+
|