Skip to content

Commit 1ac37fc

Browse files
authored
Merge pull request #109 from cokelaer/main
add levenshtein function
2 parents 09c5cbe + 1958859 commit 1ac37fc

File tree

13 files changed

+79
-20
lines changed

13 files changed

+79
-20
lines changed

README.rst

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ The **sequana_pipetools** package provide a standalone called **sequana_pipetool
110110

111111
.. figure:: https://raw.githubusercontent.com/sequana/sequana_pipetools/main/doc/UI.png
112112

113-
There are currently 3-4 main application. The first one is for Linux users under
113+
There are several applications. The first one is for Linux users under
114114
bash to obtain completion of a sequana pipeline command line arguments::
115115

116116
sequana_pipetools --completion fastqc
@@ -126,7 +126,7 @@ This is used within th pipeline but can be used manually as well and is useful t
126126
The following command provides statistics about Sequana pipelines installed on your system (number of rules, wrappers
127127
used)::
128128

129-
sequana_pipetools -- stats
129+
sequana_pipetools --stats
130130

131131
And for developpers, a quick creation of schema file given a config file (experimental, developers would still need to edit the schema but it does 90% of the job)::
132132

@@ -283,15 +283,14 @@ so, you will need to create an environment variable::
283283

284284
export SEQUANA_WRAPPERS="git+file:///home/user/github/sequana-wrappers"
285285

286-
If you decide to use singularity/apptainer, one common error on a cluster is that non-standard paths are not found. You can bind them using the -B option but a more general set up is to create thos environment variable::
286+
If you decide to use singularity/apptainer, one common error on a cluster is that non-standard paths are not found. You can bind them using the -B option but a more general set up is to create this environment variable::
287287

288288
export SINGULARITY_BINDPATH="/path_to_bind"
289289

290-
for Singularity setup, or ::
290+
for Apptainer setup ::
291291

292292
export APPTAINER_BINDPATH="/path_to_bind"
293293

294-
for Apptainer setup.
295294

296295

297296
What is Sequana ?
@@ -318,6 +317,7 @@ Changelog
318317
========= ======================================================================
319318
Version Description
320319
========= ======================================================================
320+
1.0.3 * add levenshtein function. some typo corrections.
321321
1.0.2 * add the dot2png command. pin docutils <0.21 due to pip error
322322
1.0.1 * hot fix in the profile creation (regression)
323323
1.0.0 * Stable release

doc/_static/logo_256x256.png

44.4 KB
Loading

doc/conf.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -157,11 +157,11 @@
157157
# html_title = None
158158

159159
# A shorter title for the navigation bar. Default is the same as html_title.
160-
html_short_title = "sequana"
160+
html_short_title = "sequana_pipetools"
161161

162162
# The name of an image file (relative to this directory) to place at the top
163163
# of the sidebar.
164-
# html_logo = "../../share/data/images/crx_logo.png"
164+
html_logo = "_static/logo_256x256.png"
165165

166166
# The name of an image file (within the static path) to use as favicon of the
167167
# docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ build-backend = "poetry.core.masonry.api"
66
#maintainer ?#maintainer email
77
[tool.poetry]
88
name = "sequana_pipetools"
9-
version = "1.0.2"
9+
version = "1.0.3"
1010
description = "A set of tools to help building or using Sequana pipelines"
1111
authors = ["Sequana Team"]
1212
license = "BSD-3"

sequana_pipetools/__init__.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,14 @@ def get_package_version(package_name):
1313

1414
from easydev.logging_tools import Logging
1515

16-
logger = Logging("sequana_pipetools", "WARNING")
16+
logger = Logging("sequana_pipetools", "WARNING", "cyan")
1717
# To keep the inheritance/propagation of levels. Logging from easydev will do
1818
# the formatting only.
1919
import colorlog
2020

2121
logger = colorlog.getLogger(logger.name)
2222

23-
from .misc import url2hash
23+
from .misc import url2hash, levenshtein_distance
2424
from .sequana_manager import SequanaManager # , get_pipeline_location
2525
from .snaketools import (
2626
Pipeline,

sequana_pipetools/info.py

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,11 +18,13 @@
1818

1919

2020
sequana_epilog = Colors().purple(
21-
"""If you use or like the Sequana project,
21+
"""\U00002139\U0000FE0F To use completion, type 'sequana_pipetools --completion NAME'
22+
23+
\u2705 If you use or like the Sequana project,
2224
please consider citing us (visit sequana.readthedocs.io for details) or use this
2325
citation:
2426
25-
Cokelaer et al, (2017), ‘Sequana’: a Set of Snakemake NGS pipelines, Journal of
27+
\U0001F4DA Cokelaer et al, (2017), ‘Sequana’: a Set of Snakemake NGS pipelines, Journal of
2628
Open Source Software, 2(16), 352, JOSS DOI doi:10.21105/joss.00352
2729
2830

sequana_pipetools/misc.py

Lines changed: 50 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,58 @@
1515

1616
from sequana_pipetools import get_package_version
1717

18-
__all__ = ["Colors", "print_version", "error", "url2hash"]
18+
__all__ = ["Colors", "print_version", "error", "url2hash", "levenshtein_distance"]
1919

2020

21+
def levenshtein_distance(token1: str, token2: str) -> int:
22+
"""Computes the Levenshtein distance between two strings using dynamic programming.
23+
24+
The Levenshtein distance is a measure of the minimum number of single-character edits
25+
(insertions, deletions, or substitutions) required to change one word into the other.
26+
27+
:param str token1: The first input string.
28+
:param str token2: The second input string.
29+
:return: Levenshtein distance between the two input strings.
30+
31+
Example::
32+
33+
>>> levenshtein_distance("kitten", "sitting")
34+
3
35+
>>> levenshtein_distance("flaw", "lawn")
36+
2
37+
38+
Notes:
39+
- The function uses a 2D list to store the distances, which requires O(m * n) space,
40+
where m and n are the lengths of the input strings.
41+
- The time complexity is O(m * n) since each cell of the matrix is filled once.
42+
43+
"""
44+
len1, len2 = len(token1), len(token2)
45+
46+
# Initialize the matrix with zeros
47+
distances = [[0 for _ in range(len2 + 1)] for _ in range(len1 + 1)]
48+
49+
# Fill the first row and column
50+
for t1 in range(len1 + 1):
51+
distances[t1][0] = t1
52+
53+
for t2 in range(len2 + 1):
54+
distances[0][t2] = t2
55+
56+
# Compute the Levenshtein distance
57+
for t1 in range(1, len1 + 1):
58+
for t2 in range(1, len2 + 1):
59+
if token1[t1 - 1] == token2[t2 - 1]:
60+
distances[t1][t2] = distances[t1 - 1][t2 - 1]
61+
else:
62+
distances[t1][t2] = min(
63+
distances[t1][t2 - 1], # Insertion
64+
distances[t1 - 1][t2], # Deletion
65+
distances[t1 - 1][t2 - 1] # Substitution
66+
) + 1
67+
68+
return distances[len1][len2]
69+
2170
def url2hash(url):
2271
md5hash = hashlib.md5()
2372
md5hash.update(url.encode())

sequana_pipetools/options.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ def from_project_callback(ctx, param, value):
198198
if not value:
199199
return
200200
else:
201-
# When --from-project is called, all value of arguments are are replaced by the ones
201+
# When --from-project is called, all value of arguments are replaced by the ones
202202
# found in the config file. Therefore, users may ommit all arguments. However, some
203203
# may be compulsary, so we need to reset all 'required' arguments to False
204204
for option in ctx.command.params:

sequana_pipetools/scripts/main.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -227,15 +227,16 @@ def main(**kwargs):
227227
subprocess.call(cmd.split())
228228

229229
elif kwargs["completion"]:
230+
name = kwargs["completion"]
231+
230232
if kwargs["force"] is True:
231233
choice = "y"
232234
else: # pragma: no cover
233-
msg = "This action will replace files stored in ./config/sequana/pipelines. Do you want to proceed y/n: "
235+
msg = f"This action will replace the {name}.sh file stored in ~/.config/sequana/pipelines. Do you want to proceed y/n: "
234236
choice = input(msg)
235237
if choice != "y": # pragma: no cover
236238
sys.exit(0)
237239

238-
name = kwargs["completion"]
239240
try:
240241
c = ClickComplete(name)
241242
c.save_completion_script()
@@ -244,7 +245,7 @@ def main(**kwargs):
244245
finally:
245246
click.echo("Please source the files using:: \n")
246247
click.echo(" source ~/.config/sequana/pipelines/{}.sh".format(name))
247-
click.echo("\nto activate the completion")
248+
click.echo("\nto activate the completion. Add the line above in your environement")
248249
elif kwargs["stats"]:
249250
wrappers, rules = get_pipeline_statistics()
250251
click.echo("\n ==== Number of wrappers per pipeline")

sequana_pipetools/snaketools/pipeline_manager.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -172,6 +172,7 @@ def teardown(self, extra_dirs_to_remove=[], extra_files_to_remove=[], outdir="."
172172
print("\u2705 Another successful analysis. Open summary.html in your browser. Have fun.")
173173
else:
174174
print("\u2705 Another successful analysis. Have fun.")
175+
print("\u2705 Please consider citing us would you use Sequana in your research. See https://sequana.readthedocs.io or cite: \n\n\tCokelaer et al. Sequana': a Set of Snakemake NGS pipelines, (2007) JOSS 2(16)")
175176

176177
def get_html_summary(self, float="left", width=30):
177178
import pandas as pd

0 commit comments

Comments
 (0)