opencloning 0.4.8__py3-none-any.whl → 0.5__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.
Files changed (37) hide show
  1. opencloning/app_settings.py +7 -0
  2. opencloning/batch_cloning/pombe/__init__.py +2 -2
  3. opencloning/batch_cloning/pombe/pombe_clone.py +31 -112
  4. opencloning/batch_cloning/pombe/pombe_summary.py +20 -8
  5. opencloning/batch_cloning/ziqiang_et_al2024/__init__.py +8 -8
  6. opencloning/batch_cloning/ziqiang_et_al2024/ziqiang_et_al2024.json +2 -9
  7. opencloning/bug_fixing/backend_v0_3.py +13 -5
  8. opencloning/catalogs/__init__.py +36 -0
  9. opencloning/catalogs/igem2024.yaml +2172 -0
  10. opencloning/catalogs/openDNA_collections.yaml +1161 -0
  11. opencloning/catalogs/readme.txt +1 -0
  12. opencloning/catalogs/seva.tsv +231 -0
  13. opencloning/catalogs/snapgene.yaml +2837 -0
  14. opencloning/dna_functions.py +155 -158
  15. opencloning/dna_utils.py +45 -62
  16. opencloning/ebic/primer_design.py +1 -1
  17. opencloning/endpoints/annotation.py +9 -13
  18. opencloning/endpoints/assembly.py +157 -378
  19. opencloning/endpoints/endpoint_utils.py +52 -0
  20. opencloning/endpoints/external_import.py +169 -124
  21. opencloning/endpoints/no_assembly.py +23 -39
  22. opencloning/endpoints/no_input.py +32 -47
  23. opencloning/endpoints/other.py +1 -1
  24. opencloning/endpoints/primer_design.py +2 -1
  25. opencloning/http_client.py +2 -2
  26. opencloning/ncbi_requests.py +113 -47
  27. opencloning/primer_design.py +1 -1
  28. opencloning/pydantic_models.py +10 -510
  29. opencloning/request_examples.py +10 -22
  30. opencloning/temp_functions.py +50 -0
  31. {opencloning-0.4.8.dist-info → opencloning-0.5.dist-info}/METADATA +18 -8
  32. opencloning-0.5.dist-info/RECORD +51 -0
  33. {opencloning-0.4.8.dist-info → opencloning-0.5.dist-info}/WHEEL +1 -1
  34. opencloning/cre_lox.py +0 -116
  35. opencloning/gateway.py +0 -154
  36. opencloning-0.4.8.dist-info/RECORD +0 -45
  37. {opencloning-0.4.8.dist-info → opencloning-0.5.dist-info}/licenses/LICENSE +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: opencloning
3
- Version: 0.4.8
3
+ Version: 0.5
4
4
  Summary: Backend of OpenCloning, a web application to generate molecular cloning strategies in json format, and share them with others.
5
5
  License: MIT
6
6
  License-File: LICENSE
@@ -17,14 +17,13 @@ Requires-Dist: beautifulsoup4 (>=4.11.1,<5.0.0)
17
17
  Requires-Dist: biopython (>=1.85,<2.0)
18
18
  Requires-Dist: fastapi
19
19
  Requires-Dist: httpx (>=0.28.1,<0.29.0)
20
- Requires-Dist: opencloning-linkml (==0.4.4)
21
20
  Requires-Dist: openpyxl (>=3.1.5,<4.0.0)
22
21
  Requires-Dist: packaging (>=25.0,<26.0)
23
22
  Requires-Dist: pairwise-alignments-to-msa (>=0.1.1,<0.2.0)
24
23
  Requires-Dist: pandas (>=2.2.3,<3.0.0)
25
- Requires-Dist: primer3-py (==2.2.0)
24
+ Requires-Dist: primer3-py (>=2.3,<3.0)
26
25
  Requires-Dist: pydantic (>=2.7.1,<3.0.0)
27
- Requires-Dist: pydna (==5.5.2)
26
+ Requires-Dist: pydna (>=5.5.5,<6.0.0)
28
27
  Requires-Dist: python-multipart
29
28
  Requires-Dist: pyyaml (>=6.0.2,<7.0.0)
30
29
  Requires-Dist: regex (>=2024.11.6,<2025.0.0)
@@ -47,9 +46,9 @@ Read [main project readme](https://github.com/manulera/OpenCloning) first.
47
46
 
48
47
  This API provides a series of entry points. The API documentation can be accessed [here](https://api.opencloning.org/docs). You can use the documentation page to try some request directly on the browser. Otherwise, the API is open for you to make requests from a python script or command line at: [https://api.opencloning.org/](https://api.opencloning.org/).
49
48
 
50
- ## Scripting
49
+ ## Scripting with pydna
51
50
 
52
- The API functions can also be used to write python scripts to automate cloning. See the [scripting examples](examples/scripting) for more information.
51
+ You can write python scripts to automate cloning using the python library [pydna](https://github.com/pydna-group/pydna), which is now integrated with the OpenCloning data model. See [the documentation](https://github.com/pydna-group/pydna/blob/master/docs/notebooks/history.ipynb) for how to get started.
53
52
 
54
53
  ## Migrating between model versions and fixing model bugs
55
54
 
@@ -117,7 +116,7 @@ docker run -d --name backendcontainer -p 8000:8000 manulera/opencloningbackend
117
116
 
118
117
  ```
119
118
 
120
- If you don't want to download the repository and build the image, you can fetch the latest image from dockerhub (same image that is used in [https://api.opencloning.org/](https://api.opencloning.org/))
119
+ If you don't want to download the repository and build the image, you can fetch the latest image from dockerhub.
121
120
 
122
121
  ```bash
123
122
  docker pull manulera/opencloningbackend
@@ -167,7 +166,7 @@ pytest -v -ks
167
166
  ### Ping a particular library version from github:
168
167
 
169
168
  ```
170
- poetry add git+https://github.com/BjornFJohansson/pydna#4fd760d075f77cceeb27969e017e04b42f6d0aa3
169
+ poetry add git+https://github.com/pydna-group/pydna#4fd760d075f77cceeb27969e017e04b42f6d0aa3
171
170
  ```
172
171
 
173
172
  When installing the last version, sometimes poetry may not be able to access the latest version
@@ -188,3 +187,14 @@ RECORD_STUBS=1 uvicorn opencloning.main:app --reload --reload-exclude='.venv'
188
187
 
189
188
  This will record the stubs (requests and responses) in the `stubs` folder.
190
189
 
190
+
191
+ ### Catalogs
192
+
193
+ Catalogs are used to map ids to urls for several plasmid collections. They are stored in the `src/opencloning/catalogs` folder.
194
+
195
+ To update the catalogs, run the following command:
196
+
197
+ ```bash
198
+ poetry run python scripts/update_catalogs.py
199
+ ```
200
+
@@ -0,0 +1,51 @@
1
+ opencloning/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
+ opencloning/_version.py,sha256=6QbWXLSZypjtWL_CwJFHH4dzMRK3AUH4B0YudzvGz9s,200
3
+ opencloning/api_config_utils.py,sha256=inAXPGYNDz-DuEoSqitImj0Vv5TpQSbMZH9D3dQb5P0,4319
4
+ opencloning/app_settings.py,sha256=O67vY7TxyKsXepOxUNc_O0JO70lf7tEL9cqIMsiTXWE,3220
5
+ opencloning/batch_cloning/__init__.py,sha256=uDxAa45g30_S6dJScNMlIxubQXlLRUsWoLX4S4y-l88,244
6
+ opencloning/batch_cloning/index.html,sha256=HDqPHrJxrrKfGmy_dwYHhOsdUgZHHIch7Z0ey8qyvZI,1332
7
+ opencloning/batch_cloning/pombe/__init__.py,sha256=dVbRBba4ZcmA1x4eEn7I5kndDImQVT6-K-iqIGaDi3c,3343
8
+ opencloning/batch_cloning/pombe/index.html,sha256=3YchoKGpcKDfvTOW1Rdih4PkbZIkMjKIQ0PaVXfV3e8,8348
9
+ opencloning/batch_cloning/pombe/pombe_clone.py,sha256=BwnEGkz9skbIqR-W0Y1iB3wYgWH35hADp0PcUTaXKUk,3985
10
+ opencloning/batch_cloning/pombe/pombe_gather.py,sha256=qI-biMZGLxVDV-vOf3sT6bS1BawtTihZNcSYNlnnEi8,2432
11
+ opencloning/batch_cloning/pombe/pombe_get_primers.py,sha256=nrn6V4_l8FWWfqS4WU3qPt95KwzvCXxETh8E-zWbRhM,3968
12
+ opencloning/batch_cloning/pombe/pombe_summary.py,sha256=GkmKZpR3fIBZd9HzyihZpITAoXgUiKe9W5l0GyLk-aU,4691
13
+ opencloning/batch_cloning/ziqiang_et_al2024/__init__.py,sha256=PPfNUth03WWeiAwlPCPD7_uTJpgWybrUpgTTkXN_jf0,7162
14
+ opencloning/batch_cloning/ziqiang_et_al2024/index.html,sha256=EDncANDhhQkhi5FjnnAP6liHkG5srf4_Y46IrnMUG5g,4607
15
+ opencloning/batch_cloning/ziqiang_et_al2024/ziqiang_et_al2024.json,sha256=uR1emjNhCDk6uYCJC4MJwz9MJ9U5RQZk9j5cKPbqNXE,156906
16
+ opencloning/bug_fixing/README.md,sha256=eak5x1NTyTxsklaZ1BzB3RYH26MC_2gNuH-gHvuNpKY,4441
17
+ opencloning/bug_fixing/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
18
+ opencloning/bug_fixing/backend_v0_3.py,sha256=_kxYPcUmBFGL1WEwtpl6ySwSSN0WRk9qZwX2Kc4eAUs,4608
19
+ opencloning/catalogs/__init__.py,sha256=hHalYzJimaHWM39RPAMGduSxSWpjHy8UBqO-utOmp88,1103
20
+ opencloning/catalogs/igem2024.yaml,sha256=CWayosovGycGCfDG-EOgPRjOMUYsDCsFy5DoHGJGwc4,49247
21
+ opencloning/catalogs/openDNA_collections.yaml,sha256=JPnPLJd9ynJkqJAumu0f7-E5E0WSDN2pjB7rNa3wJLA,38655
22
+ opencloning/catalogs/readme.txt,sha256=SPBPLfqszGH0zl7EZYddNwi9nE90or82o8aHNMscSkw,87
23
+ opencloning/catalogs/seva.tsv,sha256=FFGZDDgsExYke1S0g_KCzM5YL680_RS-1XNEJbiqFJo,16125
24
+ opencloning/catalogs/snapgene.yaml,sha256=Zi0i4l9KBOhoHnr7i2nYWD58IIYgBbEaNF5m4qzm2ks,47359
25
+ opencloning/dna_functions.py,sha256=vyy2UDyYj3IfVmWf1z07j8T7D53JM-wFQFawcLzZt-k,15967
26
+ opencloning/dna_utils.py,sha256=n_XRBr9xeEQSoMUWdgH7UigZN2KtU7AxmIwW18aFQdY,6814
27
+ opencloning/ebic/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
28
+ opencloning/ebic/primer_design.py,sha256=e_PkEhnlkeV7D3iCeDL8s1p-FkNWj17zWNaq-x9Uz8E,3149
29
+ opencloning/ebic/primer_design_settings.py,sha256=OnFsuh0QCvplUEPXLZouzRo9R7rm4nLbcd2LkDCiIDM,1896
30
+ opencloning/endpoints/annotation.py,sha256=_jQGvwcP-LvoLJKaRG2_YyMLyOzk1R9lUlYNHFc7afY,2126
31
+ opencloning/endpoints/assembly.py,sha256=e6PFNp0ZmAQ7niI54vAZkuTgjTg1NIf0vCnVfebF184,13373
32
+ opencloning/endpoints/endpoint_utils.py,sha256=KIbYA-XPFArHzVTQ8RfxDR4eI3WypOZPJx64_GmjGHY,2061
33
+ opencloning/endpoints/external_import.py,sha256=IdhI1mBvBF77v6DB4Sfc5-RSzW90MzGjTc-zX7aeaxI,19671
34
+ opencloning/endpoints/no_assembly.py,sha256=dOyfh_nfQOmnJx6Vwhwo7EBIIbMRwGf_Ap_VsjSQc40,4031
35
+ opencloning/endpoints/no_input.py,sha256=1NSiuyS2zWwK3Ae34tFChhqEZ7645w75ibNW9RREYVw,3752
36
+ opencloning/endpoints/other.py,sha256=e_GXJDnqQFREU9GcOruI-8yQJpK-eVtDH1ZiVPL7WQU,4028
37
+ opencloning/endpoints/primer_design.py,sha256=2XSflQXQ1vOqY6vyvalrOU3baC2-fn-oSV5294c5cXI,13017
38
+ opencloning/get_router.py,sha256=l2DXaTbeL2tDqlnVMlcewutzt1sjaHlxku1X9HVUwJk,252
39
+ opencloning/http_client.py,sha256=9f0mqYPwQmWr0B6hMSoYT80g4RT2itKA2iokAknY5yY,1239
40
+ opencloning/main.py,sha256=l9PrPBMtGMEWxAPiPWR15Qv2oDNnRoNd8H8E3bZW6Do,3750
41
+ opencloning/ncbi_requests.py,sha256=jO3UWlGMENE3YPDCfo-pZWO5iJa1C0x7rahIf0cLCRk,8936
42
+ opencloning/primer3_functions.py,sha256=R29jic_tb7qhXnDb4RGCx2xaViVCnxTyaVU89KMUIjQ,3584
43
+ opencloning/primer_design.py,sha256=vHi4cBjxEOimzEABvt0sEcDZeXvZLkpnj7k9K7qu9qw,9249
44
+ opencloning/pydantic_models.py,sha256=cKXRHQyPdQDxkdzEwKgwvmQy0UjFjDVFR-eKIsBSZbE,2964
45
+ opencloning/request_examples.py,sha256=rg-v9a5ttzwu5tKY5h3tiT_kVkIZOicS8c01MxrEcEY,2653
46
+ opencloning/temp_functions.py,sha256=wRh26uW_JT9sy3070jIizTT82CE_hS8-GRW3vXEd1GQ,2029
47
+ opencloning/utils.py,sha256=0Lvw1h1AsUJTK2b9mNzYVi_DBeWmWCFA5dIPl_gERcI,1479
48
+ opencloning-0.5.dist-info/METADATA,sha256=4ZQGH31rO4f_p9WIxTpu7UfKK8H6D1D_YilCscz1XUc,9501
49
+ opencloning-0.5.dist-info/WHEEL,sha256=3ny-bZhpXrU6vSQ1UPG34FoxZBp3lVcvK0LkgUz6VLk,88
50
+ opencloning-0.5.dist-info/licenses/LICENSE,sha256=VSdVE1f8axjIh6gvo9ZZygJdTVkRFMcwCW_hvjOHC_w,1058
51
+ opencloning-0.5.dist-info/RECORD,,
@@ -1,4 +1,4 @@
1
1
  Wheel-Version: 1.0
2
- Generator: poetry-core 2.2.1
2
+ Generator: poetry-core 2.3.0
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
opencloning/cre_lox.py DELETED
@@ -1,116 +0,0 @@
1
- from itertools import product
2
- from pydna.dseqrecord import Dseqrecord
3
- from Bio.Data.IUPACData import ambiguous_dna_values
4
- from Bio.Seq import reverse_complement
5
- from .dna_utils import compute_regex_site, dseqrecord_finditer
6
- from Bio.SeqFeature import Location, SimpleLocation, SeqFeature
7
- from pydna.utils import shift_location
8
-
9
- # We create a dictionary to map ambiguous bases to their consensus base
10
- # For example, ambigous_base_dict['ACGT'] -> 'N'
11
- ambiguous_base_dict = {}
12
- for ambiguous, bases in ambiguous_dna_values.items():
13
- ambiguous_base_dict[''.join(sorted(bases))] = ambiguous
14
-
15
- # To handle N values
16
- ambiguous_base_dict['N'] = 'N'
17
-
18
- # This is the original loxP sequence, here for reference
19
- LOXP_SEQUENCE = 'ATAACTTCGTATAGCATACATTATACGAAGTTAT'
20
-
21
- loxP_sequences = [
22
- # https://blog.addgene.org/plasmids-101-cre-lox
23
- # loxP
24
- 'ATAACTTCGTATANNNTANNNTATACGAAGTTAT',
25
- # PMID:12202778
26
- # lox66
27
- 'ATAACTTCGTATANNNTANNNTATACGAACGGTA',
28
- # lox71
29
- 'TACCGTTCGTATANNNTANNNTATACGAAGTTAT',
30
- ]
31
-
32
- loxP_consensus = ''
33
-
34
- for pos in range(len(LOXP_SEQUENCE)):
35
- all_letters = set(seq[pos] for seq in loxP_sequences)
36
- key = ''.join(sorted(all_letters))
37
- loxP_consensus += ambiguous_base_dict[key]
38
-
39
- # We compute the regex for the forward and reverse loxP sequences
40
- loxP_regex = (compute_regex_site(loxP_consensus), compute_regex_site(reverse_complement(loxP_consensus)))
41
-
42
-
43
- def cre_loxP_overlap(x: Dseqrecord, y: Dseqrecord, _l: None = None) -> list[tuple[int, int, int]]:
44
- """Find matching loxP sites between two sequences."""
45
- out = list()
46
- for pattern in loxP_regex:
47
- matches_x = dseqrecord_finditer(pattern, x)
48
- matches_y = dseqrecord_finditer(pattern, y)
49
-
50
- for match_x, match_y in product(matches_x, matches_y):
51
- value_x = match_x.group()
52
- value_y = match_y.group()
53
- if value_x[13:21] == value_y[13:21]:
54
- out.append((match_x.start() + 13, match_y.start() + 13, 8))
55
- # Unique values (keeping the order)
56
- unique_out = []
57
- for item in out:
58
- if item not in unique_out:
59
- unique_out.append(item)
60
- return unique_out
61
-
62
-
63
- loxP_dict = {
64
- 'loxP': 'ATAACTTCGTATANNNTANNNTATACGAAGTTAT',
65
- 'lox66': 'ATAACTTCGTATANNNTANNNTATACGAACGGTA',
66
- 'lox71': 'TACCGTTCGTATANNNTANNNTATACGAAGTTAT',
67
- 'loxP_mutant': 'TACCGTTCGTATANNNTANNNTATACGAACGGTA',
68
- }
69
-
70
-
71
- def get_regex_dict(original_dict: dict[str, str]) -> dict[str, str]:
72
- """Get the regex dictionary for the original dictionary."""
73
- out = dict()
74
- for site in original_dict:
75
- consensus_seq = original_dict[site]
76
- is_palindromic = consensus_seq == reverse_complement(consensus_seq)
77
- out[site] = {
78
- 'forward_regex': compute_regex_site(original_dict[site]),
79
- 'reverse_regex': None if is_palindromic else compute_regex_site(reverse_complement(original_dict[site])),
80
- }
81
- return out
82
-
83
-
84
- def find_loxP_sites(seq: Dseqrecord) -> dict[str, list[Location]]:
85
- """Find all gateway sites in a sequence and return a dictionary with the name and positions of the sites."""
86
-
87
- out = dict()
88
- regex_dict = get_regex_dict(loxP_dict)
89
- for site in loxP_dict:
90
-
91
- for pattern in ['forward_regex', 'reverse_regex']:
92
- # Palindromic sequences have no reverse complement
93
- if regex_dict[site][pattern] is None:
94
- continue
95
- matches = list(dseqrecord_finditer(regex_dict[site][pattern], seq))
96
- for match in matches:
97
- if site not in out:
98
- out[site] = []
99
- strand = 1 if pattern == 'forward_regex' else -1
100
- loc = SimpleLocation(match.start(), match.end(), strand)
101
- loc = shift_location(loc, 0, len(seq))
102
- out[site].append(loc)
103
- return out
104
-
105
-
106
- def annotate_loxP_sites(seq: Dseqrecord) -> Dseqrecord:
107
- sites = find_loxP_sites(seq)
108
- for site in sites:
109
- for loc in sites[site]:
110
- # Don't add the same feature twice
111
- if not any(
112
- f.location == loc and f.type == 'protein_bind' and f.qualifiers.get('label', []) == [site]
113
- for f in seq.features
114
- ):
115
- seq.features.append(SeqFeature(loc, type='protein_bind', qualifiers={'label': [site]}))
116
- return seq
opencloning/gateway.py DELETED
@@ -1,154 +0,0 @@
1
- from Bio.Seq import reverse_complement
2
- from pydna.dseqrecord import Dseqrecord as _Dseqrecord
3
- import re
4
- import itertools as _itertools
5
- from Bio.SeqFeature import SimpleLocation, SeqFeature
6
- from pydna.utils import shift_location
7
- from .dna_utils import compute_regex_site, dseqrecord_finditer
8
-
9
-
10
- raw_gateway_common = {
11
- 'attB1': 'CHWVTWTGTACAAAAAANNNG',
12
- 'attB2': 'CHWVTWTGTACAAGAAANNNG',
13
- 'attB3': 'CHWVTWTGTATAATAAANNNG',
14
- 'attB4': 'CHWVTWTGTATAGAAAANNNG',
15
- 'attB5': 'CHWVTWTGTATACAAAANNNG',
16
- 'attL1': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTACAAAAAANNNG',
17
- 'attL2': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTACAAGAAANNNG',
18
- 'attL3': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATAATAAANNNG',
19
- 'attL4': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATAGAAAANNNG',
20
- 'attL5': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATACAAAANNNG',
21
- 'attR1': 'CHWVTWTGTACAAAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
22
- 'attR2': 'CHWVTWTGTACAAGAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
23
- 'attR3': 'CHWVTWTGTATAATAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
24
- 'attR4': 'CHWVTWTGTATAGAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
25
- 'attR5': 'CHWVTWTGTATACAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
26
- 'overlap_1': 'twtGTACAAAaaa',
27
- 'overlap_2': 'twtGTACAAGaaa',
28
- 'overlap_3': 'twtGTATAATaaa',
29
- 'overlap_4': 'twtGTATAGAaaa',
30
- 'overlap_5': 'twtGTATACAaaa',
31
- }
32
-
33
-
34
- raw_gateway_sites_greedy = {
35
- **raw_gateway_common,
36
- 'attP1': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTACAAAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
37
- 'attP2': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTACAAGAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
38
- 'attP3': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATAATAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
39
- 'attP4': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATAGAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
40
- 'attP5': 'VAAWWAWKRWTTTWWTTYGACTGATAGTGACCTGTWCGTYGMAACAVATTGATRAGCAATKMTTTYYTATAWTGHCMASTWTGTATACAAAAGYWGARCGAGAARCGTAARRTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATRCTGTAARACACAACATATBCAGTCV',
41
- }
42
-
43
- raw_gateway_sites_conservative = {
44
- **raw_gateway_common,
45
- 'attP1': 'AAAWWAWKRWTTTWWTTTGACTGATAGTGACCTGTTCGTTGCAACAMATTGATRAGCAATGCTTTYTTATAATGCCMASTTTGTACAAAAAAGYWGAACGAGAARCGTAAARTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATACTGTAAAACACAACATATSCAGTCACTATGAAYCAACTACTTAGATGGTATTAGTGACCTGTA',
46
- 'attP2': 'AAAWWAWKRWTTTWWTTTGACTGATAGTGACCTGTTCGTTGCAACAMATTGATRAGCAATGCTTTYTTATAATGCCMASTTTGTACAAGAAAGYWGAACGAGAARCGTAAARTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATACTGTAAAACACAACATATSCAGTCACTATGAAYCAACTACTTAGATGGTATTAGTGACCTGTA',
47
- 'attP3': 'AAAWWAWKRWTTTWWTTTGACTGATAGTGACCTGTTCGTTGCAACAMATTGATRAGCAATGCTTTYTTATAATGCCMASTTTGTATAATAAAGYWGAACGAGAARCGTAAARTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATACTGTAAAACACAACATATSCAGTCACTATGAAYCAACTACTTAGATGGTATTAGTGACCTGTA',
48
- 'attP4': 'AAAWWAWKRWTTTWWTTTGACTGATAGTGACCTGTTCGTTGCAACAMATTGATRAGCAATGCTTTYTTATAATGCCMASTTTGTATAGAAAAGYWGAACGAGAARCGTAAARTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATACTGTAAAACACAACATATSCAGTCACTATGAAYCAACTACTTAGATGGTATTAGTGACCTGTA',
49
- 'attP5': 'AAAWWAWKRWTTTWWTTTGACTGATAGTGACCTGTTCGTTGCAACAMATTGATRAGCAATGCTTTYTTATAATGCCMASTTTGTATACAAAAGYWGAACGAGAARCGTAAARTGATATAAATATCAATATATTAAATTAGAYTTTGCATAAAAAACAGACTACATAATACTGTAAAACACAACATATSCAGTCACTATGAAYCAACTACTTAGATGGTATTAGTGACCTGTA',
50
- }
51
-
52
- gateway_sites_greedy = {
53
- k: {
54
- 'forward_regex': compute_regex_site(v),
55
- 'reverse_regex': compute_regex_site(reverse_complement(v)),
56
- 'consensus_sequence': v,
57
- }
58
- for k, v in raw_gateway_sites_greedy.items()
59
- }
60
-
61
- gateway_sites_conservative = {
62
- k: {
63
- 'forward_regex': compute_regex_site(v),
64
- 'reverse_regex': compute_regex_site(reverse_complement(v)),
65
- 'consensus_sequence': v,
66
- }
67
- for k, v in raw_gateway_sites_conservative.items()
68
- }
69
-
70
- # From snapgene - ask Valerie
71
- primer_design_attB = {
72
- 'attB1': 'ACAAGTTTGTACAAAAAAGCAGGCT',
73
- 'attB2': 'ACCACTTTGTACAAGAAAGCTGGGT',
74
- 'attB3': 'ACAACTTTGTATAATAAAGTTGTA',
75
- 'attB4': 'ACAACTTTGTATAGAAAAGTTGTA',
76
- 'attB5': 'ACAACTTTGTATACAAAAGTTGTA',
77
- }
78
-
79
-
80
- def gateway_overlap(seqx: _Dseqrecord, seqy: _Dseqrecord, reaction: str, greedy: bool) -> list[tuple[int, int, int]]:
81
- """Find gateway overlaps"""
82
- if reaction not in ['BP', 'LR']:
83
- raise ValueError(f'Invalid overlap type: {reaction}')
84
-
85
- gateway_sites = gateway_sites_greedy if greedy else gateway_sites_conservative
86
- out = list()
87
- # Iterate over the four possible att sites
88
- for num in range(1, 5):
89
- # Iterate over the two possible orientations
90
- # The sites have to be in the same orientation (fwd + fwd or rev + rev)
91
- for pattern in ['forward_regex', 'reverse_regex']:
92
- # The overlap regex is the same for all types
93
- overlap_regex = gateway_sites[f'overlap_{num}'][pattern]
94
-
95
- # Iterate over pairs B, P and P, B for BP and L, R and R, L for LR
96
- for site_x, site_y in zip(reaction, reaction[::-1]):
97
- site_x_regex = gateway_sites[f'att{site_x}{num}'][pattern]
98
- matches_x = list(dseqrecord_finditer(site_x_regex, seqx))
99
- if len(matches_x) == 0:
100
- continue
101
-
102
- site_y_regex = gateway_sites[f'att{site_y}{num}'][pattern]
103
- matches_y = list(dseqrecord_finditer(site_y_regex, seqy))
104
- if len(matches_y) == 0:
105
- continue
106
-
107
- for match_x, match_y in _itertools.product(matches_x, matches_y):
108
- # Find the overlap sequence within each match, and use the
109
- # core 7 pbs that are constant
110
- overlap_x = re.search(overlap_regex, match_x.group())
111
- overlap_y = re.search(overlap_regex, match_y.group())
112
-
113
- # Sanity check
114
- assert (
115
- overlap_x is not None and overlap_y is not None
116
- ), 'Something went wrong, no overlap found within the matches'
117
-
118
- out.append(
119
- (
120
- match_x.start() + overlap_x.start() + 3,
121
- match_y.start() + overlap_y.start() + 3,
122
- 7,
123
- )
124
- )
125
-
126
- return out
127
-
128
-
129
- def find_gateway_sites(seq: _Dseqrecord, greedy: bool) -> dict[str, list[SimpleLocation]]:
130
- """Find all gateway sites in a sequence and return a dictionary with the name and positions of the sites."""
131
- gateway_sites = gateway_sites_greedy if greedy else gateway_sites_conservative
132
- out = dict()
133
- for site in gateway_sites:
134
- if not site.startswith('att'):
135
- continue
136
-
137
- for pattern in ['forward_regex', 'reverse_regex']:
138
- matches = list(dseqrecord_finditer(gateway_sites[site][pattern], seq))
139
- for match in matches:
140
- if site not in out:
141
- out[site] = []
142
- strand = 1 if pattern == 'forward_regex' else -1
143
- loc = SimpleLocation(match.start(), match.end(), strand)
144
- loc = shift_location(loc, 0, len(seq))
145
- out[site].append(loc)
146
- return out
147
-
148
-
149
- def annotate_gateway_sites(seq: _Dseqrecord, greedy: bool) -> _Dseqrecord:
150
- sites = find_gateway_sites(seq, greedy)
151
- for site in sites:
152
- for loc in sites[site]:
153
- seq.features.append(SeqFeature(loc, type='protein_bind', qualifiers={'label': [site]}))
154
- return seq
@@ -1,45 +0,0 @@
1
- opencloning/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
- opencloning/_version.py,sha256=6QbWXLSZypjtWL_CwJFHH4dzMRK3AUH4B0YudzvGz9s,200
3
- opencloning/api_config_utils.py,sha256=inAXPGYNDz-DuEoSqitImj0Vv5TpQSbMZH9D3dQb5P0,4319
4
- opencloning/app_settings.py,sha256=6gtIgDIVA9FzfBCnv8IJrEkroTjg4qdAGI4lNdxoA9E,2970
5
- opencloning/batch_cloning/__init__.py,sha256=uDxAa45g30_S6dJScNMlIxubQXlLRUsWoLX4S4y-l88,244
6
- opencloning/batch_cloning/index.html,sha256=HDqPHrJxrrKfGmy_dwYHhOsdUgZHHIch7Z0ey8qyvZI,1332
7
- opencloning/batch_cloning/pombe/__init__.py,sha256=Fq7SroO0Fer5CtFBRWdduIvzp1_dTUZwBb8IjBtRQO0,3332
8
- opencloning/batch_cloning/pombe/index.html,sha256=3YchoKGpcKDfvTOW1Rdih4PkbZIkMjKIQ0PaVXfV3e8,8348
9
- opencloning/batch_cloning/pombe/pombe_clone.py,sha256=JlaTKcPBH8pR94FVgTPCopGRBCjS2VKvkkxZLjJdyb4,8056
10
- opencloning/batch_cloning/pombe/pombe_gather.py,sha256=qI-biMZGLxVDV-vOf3sT6bS1BawtTihZNcSYNlnnEi8,2432
11
- opencloning/batch_cloning/pombe/pombe_get_primers.py,sha256=nrn6V4_l8FWWfqS4WU3qPt95KwzvCXxETh8E-zWbRhM,3968
12
- opencloning/batch_cloning/pombe/pombe_summary.py,sha256=DBpoSEV1xPFm8TFDhrxS4tjqxJVrfH-ttM_0ELjQqok,4350
13
- opencloning/batch_cloning/ziqiang_et_al2024/__init__.py,sha256=9-aG8JfZx8Y91qUAchTqRL2Rq5lSrZ34O_VkD8WNyiY,7083
14
- opencloning/batch_cloning/ziqiang_et_al2024/index.html,sha256=EDncANDhhQkhi5FjnnAP6liHkG5srf4_Y46IrnMUG5g,4607
15
- opencloning/batch_cloning/ziqiang_et_al2024/ziqiang_et_al2024.json,sha256=JAOe35VPeG3QF1CnDzZxOzqpBTSpeCCtAo2W1mVOFEo,157159
16
- opencloning/bug_fixing/README.md,sha256=eak5x1NTyTxsklaZ1BzB3RYH26MC_2gNuH-gHvuNpKY,4441
17
- opencloning/bug_fixing/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
18
- opencloning/bug_fixing/backend_v0_3.py,sha256=GfuDRvlmcSBv9emXZSWqW-SktOeI1xH-tl2UET-BSoY,4145
19
- opencloning/cre_lox.py,sha256=x_OVYzfaLJH5eVyp05_I9YNycT606UL683AswhQ-gjU,4294
20
- opencloning/dna_functions.py,sha256=O5H5DilNUOIzH8gVFiOuG8SVlrenrbwyo9lKwfxIHnY,16663
21
- opencloning/dna_utils.py,sha256=NSS_b5q8u8XNzVqCwzCQaxj4I2xHf_Inmw7iBWS9gc8,6746
22
- opencloning/ebic/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
23
- opencloning/ebic/primer_design.py,sha256=DpRD5YjA_5oFi-NLSYGGS7IDT_GkN2hYzEKiiBfyEjo,3128
24
- opencloning/ebic/primer_design_settings.py,sha256=OnFsuh0QCvplUEPXLZouzRo9R7rm4nLbcd2LkDCiIDM,1896
25
- opencloning/endpoints/annotation.py,sha256=3rlIXeNQzoqPD9lJUEBGLGxvlhUCTcfkqno814A8P0U,2283
26
- opencloning/endpoints/assembly.py,sha256=xkvChfwspdh2lnCi9tQFfTQuEhJfNXNjDb4wRKymZV8,21727
27
- opencloning/endpoints/external_import.py,sha256=Fdjj6zu0bdZg8vRi1f5bMejnKNBlt3So-BxaeD1CLxk,19115
28
- opencloning/endpoints/no_assembly.py,sha256=F6mRZFGUAASZ0v7EhPyBgmn_O-YLySMR1a_0aUH2U70,4806
29
- opencloning/endpoints/no_input.py,sha256=0wc5sTD6nL0SrsXmT__x0g-m6m45ID5hq-D8KDKy98Y,4170
30
- opencloning/endpoints/other.py,sha256=KvsrfaZXmZcfh3R7mCovuoe62O66EXKEb0pZaEAAYr8,3992
31
- opencloning/endpoints/primer_design.py,sha256=Ni3B6JTWEFBDU4bHYtygFwXR09vPjhVzboGeP70TSls,12957
32
- opencloning/gateway.py,sha256=pFB3gsCQL715kOFOP1NQOOsQqrkWuQe5qXk4IunF5SA,8486
33
- opencloning/get_router.py,sha256=l2DXaTbeL2tDqlnVMlcewutzt1sjaHlxku1X9HVUwJk,252
34
- opencloning/http_client.py,sha256=m8LPCxT4b63XPOWGAMmecaNZ7Ho1uxzJm8z7bbhOMqY,1261
35
- opencloning/main.py,sha256=l9PrPBMtGMEWxAPiPWR15Qv2oDNnRoNd8H8E3bZW6Do,3750
36
- opencloning/ncbi_requests.py,sha256=e-sBVaaWJmJpqZ3TDtZEx9C9jiZSJy69UdLcdsHzXjc,5932
37
- opencloning/primer3_functions.py,sha256=R29jic_tb7qhXnDb4RGCx2xaViVCnxTyaVU89KMUIjQ,3584
38
- opencloning/primer_design.py,sha256=9h69bwYem8HEqhp30vEnTP5TrfCISVFTwPQdgUAkS1E,9227
39
- opencloning/pydantic_models.py,sha256=SZDFrITTELkel3jOu9YlPC27RsJHzaAXTEYOMEZvvqs,20048
40
- opencloning/request_examples.py,sha256=_VvY4lNpgqhLTM6O_OUs1TujhL7RUbRFZ9ptyssbxLk,2934
41
- opencloning/utils.py,sha256=0Lvw1h1AsUJTK2b9mNzYVi_DBeWmWCFA5dIPl_gERcI,1479
42
- opencloning-0.4.8.dist-info/METADATA,sha256=YXuwg3KnCyYe4aGPi2b0xTCGU4tqu5-TMs7FBbFsWso,9211
43
- opencloning-0.4.8.dist-info/WHEEL,sha256=zp0Cn7JsFoX2ATtOhtaFYIiE2rmFAD4OcMhtUki8W3U,88
44
- opencloning-0.4.8.dist-info/licenses/LICENSE,sha256=VSdVE1f8axjIh6gvo9ZZygJdTVkRFMcwCW_hvjOHC_w,1058
45
- opencloning-0.4.8.dist-info/RECORD,,