# Writing a python module to run Infernal on a list of fasta files

I am very new to using python3 and am hoping to use it to reduce the time I need to spend running Infernal to look for a variety of RNAs in a large collection of bacterial genomes. I am hoping to write a short module in python that will let me sequentially run infernal using a single covariance model on a list of genome files.

At the moment I am trying to use subprocess.run() or subprocess.Popen() to do so.


import subprocess
import os
import glob

genomes = list(glob.glob(os.path.join("/path/to/genomes/", "*.fa")))

for x in files:
subprocess.Popen(args=["cmsearch", "/path/to/covariancemodel/", "genomes"], shell=False)


my issue is I do not know a way to have "genomes" passed as the components of the list within the command.

Is this a way off approach to trying to automate this? If so is there a better way to do it or is there a way to simply pass each file in the list to the cmsearch command?

• what delimiter does cmsearch expect? is the list separated with spaces, commas etc? 1 2 3 or 1,2,3 or 1, 2, 3 or something else? – Bioathlete Feb 5 '20 at 22:39
• The output of genomes = list(glob.glob(os.path.join("/path/to/genomes/", "*.fa"))) is comma delimted eg. /path/genome1.fa, /path/genome2.fa, ... For cmsearch it normal just takes a single file so you would use the command: cmsearch /path/to/covariancemodel.cm /path/to/genomefile.fa What I am hoping to do is replace that single genomefile.fa with each of the genome files in the genomes list. I hope that is clear! Thanks for the help. – DavidM Feb 5 '20 at 23:01
• You might be interested in a tool like snakemake. – bli Feb 10 '20 at 13:13

I think what you want to do is:

import subprocess
import os
import glob

genomes = glob.glob(os.path.join("/path/to/genomes/", "*.fa"))

for gfile in genomes:
subprocess.Popen(args=["cmsearch", "/path/to/covariancemodel/", gfile], shell=False)


each pass through the for loop will take a one of the genome files and pass it into the cmsearch command.

Note:

1) glob.glob returns a list so no need to cast it again - https://docs.python.org/2/library/glob.html

• Thank you very much for the response! I ended up solving it a slightly different way with for x in genomes: subprocess.Popen(args=["cmsearch", "/path/to/covariancemodel/", "%s" %x], shell=False) but I just gave your recommendation and it works great and cleans things up a bit! – DavidM Feb 6 '20 at 4:21
• ok you shouldn't need "%s" %x since the values within the genomes list are already string. Also str(variable) it the preferred way to convert and variable to a string – Bioathlete Feb 6 '20 at 16:56