bio-polyploid-tools 0.5.2 → 0.6.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 23c185fa7183010bca4c619fa252ecd2d58e2d13
4
- data.tar.gz: a093ad10be19c610df004bc2b0ad8834dcd7ca00
3
+ metadata.gz: 76d57ca94d667e3aff5324977e57d8b7a5f0d91e
4
+ data.tar.gz: ccd2fad348fbc8a68927b944adc8e13b7d776edf
5
5
  SHA512:
6
- metadata.gz: 7b6838728afb273a71afc44bfe790c947662c0d432229e3d40f7dca34e67928a849a95c9f52c90562b509e3ef1aa9d51147c7c60de49573baf826695cc425365
7
- data.tar.gz: 4941e7ca5027e0fed010dcd6523f82fafc1a8db75a9826f4c14f6fef20a54e79f614d91560cf398174e23ebbe1f2c71b80916ba118ae28ed50fe4a451f3c8410
6
+ metadata.gz: 99edd393245dc13ebf8b10abab165c86a9e808f5cabfe95fccd6607360383d79c277a84e37c831782412817ac35b82dddde717448510dbd5f89b4e5a268640d9
7
+ data.tar.gz: c387e7b9a9b8d5c6bbb8e286a2fa71e4ecd92093578e58d04d260f5d8f7ba66f47d03856486c030f91488f39078129b27f600329596faec2183e0c521eaf6785
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.5.2
1
+ 0.6.0
data/bin/polymarker.rb CHANGED
@@ -36,6 +36,8 @@ options[:bucket] = 1
36
36
  options[:model] = "est2genome"
37
37
  options[:arm_selection] = arm_selection_functions[:arm_selection_embl] ;
38
38
  options[:flanking_size] = 150;
39
+ options[:variation_free_region] = 0
40
+ options[:extract_found_contigs] = false
39
41
  options[:primer_3_preferences] = {
40
42
  :primer_product_size_range => "50-150" ,
41
43
  :primer_max_size => 25 ,
@@ -60,6 +62,11 @@ OptionParser.new do |opts|
60
62
  opts.on("-s", "--snp_list FILE", "File with the list of snps to search from, requires --reference to get the sequence using a position") do |o|
61
63
  options[:snp_list] = o
62
64
  end
65
+
66
+ opts.on("-t", "--mutant_list FILE", "File with the list of positions with mutation and the mutation line.\n\
67
+ requires --reference to get the sequence using a position") do |o|
68
+ options[:mutant_list] = o
69
+ end
63
70
 
64
71
  opts.on("-r", "--reference FILE", "Fasta file with the sequence for the markers (to complement --snp_list)") do |o|
65
72
  options[:reference] = o
@@ -71,9 +78,9 @@ OptionParser.new do |opts|
71
78
 
72
79
  opts.on("-e", "--exonerate_model MODEL", "Model to be used in exonerate to search for the contigs") do |o|
73
80
  options[:model] = o
74
- end
81
+ end
75
82
 
76
- opts.on("-a", "--arm_selection arm_selection_embl|arm_selection_morex|arm_selection_first_two", "Function to decide the chromome arm") do |o|
83
+ opts.on("-a", "--arm_selection arm_selection_embl|arm_selection_morex|arm_selection_first_two", "Function to decide the chromome arm") do |o|
77
84
  options[:arm_selection] = arm_selection_functions[o.to_sym];
78
85
  end
79
86
 
@@ -81,8 +88,20 @@ OptionParser.new do |opts|
81
88
  options[:primer_3_preferences] = Bio::DB::Primer3.read_primer_preferences(o, options[:primer_3_preferences] )
82
89
  end
83
90
 
91
+ opts.on("-v", "--variation_free_region INT", "If present, avoid generating the common primer if there are homoeologous SNPs within the specified distance") do |o|
92
+ options[:variation_free_region] = o.to_i
93
+ end
94
+
95
+ opts.on("-x", "--extract_found_contigs", "If present, save in a separate file the contigs with matches. Useful to debug.") do |o|
96
+ options[:extract_found_contigs] = true
97
+ end
98
+
99
+ opts.on("-P", "--primers_to_order")do
100
+ #TODO: have a string with the tails, optional.
101
+ options[:primers_to_order] = true
102
+ end
103
+
84
104
 
85
-
86
105
  end.parse!
87
106
 
88
107
  if options[:primer_3_preferences][:primer_product_size_range]
@@ -108,8 +127,9 @@ snp_in="B"
108
127
 
109
128
  fasta_reference = nil
110
129
  #test_file="/Users/ramirezr/Dropbox/JIC/PrimersToTest/test_primers_nick_and_james_1.csv"
111
- test_file=options[:marker_list]
130
+ test_file=options[:marker_list] if options[:marker_list]
112
131
  test_file=options[:snp_list] if options[:snp_list]
132
+ test_file=options[:mutant_list] if options[:mutant_list]
113
133
  fasta_reference = options[:reference]
114
134
  output_folder="#{test_file}_primer_design_#{Time.now.strftime('%Y%m%d-%H%M%S')}"
115
135
  output_folder= options[:output_folder] if options[:output_folder]
@@ -122,12 +142,12 @@ primer_3_input="#{output_folder}/primer_3_input_temp"
122
142
  primer_3_output="#{output_folder}/primer_3_output_temp"
123
143
  exons_filename="#{output_folder}/exons_genes_and_contigs.fa"
124
144
  output_primers="#{output_folder}/primers.csv"
145
+ output_to_order="#{output_folder}/primers_to_order.csv"
125
146
  @status_file="#{output_folder}/status.txt"
126
147
 
127
148
  primer_3_config=File.expand_path(File.dirname(__FILE__) + '/../conf/primer3_config')
128
149
  model=options[:model]
129
150
 
130
-
131
151
  def write_status(status)
132
152
  f=File.open(@status_file, "a")
133
153
  f.puts "#{Time.now.to_s},#{status}"
@@ -148,9 +168,6 @@ if fasta_reference
148
168
  p "Fasta reference: #{fasta_reference}"
149
169
  end
150
170
 
151
-
152
-
153
-
154
171
  #1. Read all the SNP files
155
172
  #chromosome = nil
156
173
  write_status "Reading SNPs"
@@ -167,13 +184,22 @@ File.open(test_file) do | f |
167
184
  region = fasta_reference_db.index.region_for_entry(snp.gene).get_full_region
168
185
  snp.template_sequence = fasta_reference_db.fetch_sequence(region)
169
186
  else
170
- $stderr.puts "ERROR: Unable to find entry for #{snp.gene}"
187
+ write_status "WARN: Unable to find entry for #{snp.gene}"
188
+ end
189
+ elsif options[:mutant_list] and options[:reference] #List and fasta file
190
+ snp = Bio::PolyploidTools::SNPMutant.parse(line)
191
+ entry = fasta_reference_db.index.region_for_entry(snp.contig)
192
+ if entry
193
+ region = fasta_reference_db.index.region_for_entry(snp.contig).get_full_region
194
+ snp.full_sequence = fasta_reference_db.fetch_sequence(region)
195
+ else
196
+ write_status "WARN: Unable to find entry for #{snp.gene}"
171
197
  end
172
-
173
198
  else
174
199
  rise Bio::DB::Exonerate::ExonerateException.new "Wrong number of arguments. "
175
200
  end
176
201
  rise Bio::DB::Exonerate::ExonerateException.new "No SNP for line '#{line}'" if snp == nil
202
+
177
203
  snp.snp_in = snp_in
178
204
  snp.original_name = original_name
179
205
  if snp.position
@@ -206,7 +232,7 @@ file.close
206
232
  #chr_group = chromosome[0]
207
233
  write_status "Searching markers in genome"
208
234
  exo_f = File.open(exonerate_file, "w")
209
- contigs_f = File.open(temp_contigs, "w")
235
+ contigs_f = File.open(temp_contigs, "w") if options[:extract_found_contigs]
210
236
  filename=path_to_contigs
211
237
  puts filename
212
238
  target=filename
@@ -224,13 +250,13 @@ Bio::DB::Exonerate.align({:query=>temp_fasta_query, :target=>target, :model=>mod
224
250
  raise ExonerateException.new, "Entry not found! #{aln.target_id}. Make sure that the #{target_id}.fai was generated properly." if entry == nil
225
251
  region = entry.get_full_region
226
252
  seq = fasta_file.fetch_sequence(region)
227
- contigs_f.puts(">#{aln.target_id}\n#{seq}")
253
+ contigs_f.puts(">#{aln.target_id}\n#{seq}") if options[:extract_found_contigs]
228
254
  end
229
255
  end
230
256
  end
231
257
 
232
- exo_f.close()
233
- contigs_f.close()
258
+ exo_f.close()
259
+ contigs_f.close() if options[:extract_found_contigs]
234
260
 
235
261
  #4. Load all the results from exonerate and get the input filename for primer3
236
262
  #Custom arm selection function that only uses the first two characters. Maybe
@@ -241,12 +267,13 @@ write_status "Reading best alignment on each chromosome"
241
267
  container= Bio::PolyploidTools::ExonContainer.new
242
268
  container.flanking_size=options[:flanking_size]
243
269
  container.gene_models(temp_fasta_query)
244
- container.chromosomes(temp_contigs)
270
+ container.chromosomes(fasta_reference)
245
271
  container.add_parental({:name=>snp_in})
246
272
  container.add_parental({:name=>original_name})
247
273
  snps.each do |snp|
248
274
  snp.container = container
249
275
  snp.flanking_size = container.flanking_size
276
+ snp.variation_free_region = options[:variation_free_region]
250
277
  container.add_snp(snp)
251
278
  end
252
279
  container.add_alignments({:exonerate_file=>exonerate_file, :arm_selection=>options[:arm_selection] , :min_identity=>min_identity})
@@ -281,6 +308,8 @@ kasp_container.add_primers_file(primer_3_output) if added_exons > 0
281
308
  header = "Marker,SNP,RegionSize,chromosome,total_contigs,contig_regions,SNP_type,#{original_name},#{snp_in},common,primer_type,orientation,#{original_name}_TM,#{snp_in}_TM,common_TM,selected_from,product_size,errors"
282
309
  File.open(output_primers, 'w') { |f| f.write("#{header}\n#{kasp_container.print_primers}") }
283
310
 
311
+ File.open(output_to_order, "w") { |io| io.write(kasp_container.print_primers_with_tails()) }
312
+
284
313
  write_status "DONE"
285
314
  rescue StandardError => e
286
315
  write_status "ERROR\t#{e.message}"
@@ -28,7 +28,7 @@ OptionParser.new do |opts|
28
28
 
29
29
  opts.banner = "Usage: snp_postion_to_polymarker.rb [options]"
30
30
 
31
- opts.on("-s", "--sno_file CSV", "CSV file with the following columnns:\nID,Allele_1,position,Allele_1,target_chromosome") do |o|
31
+ opts.on("-s", "--snp_file CSV", "CSV file with the following columnns:\nID,Allele_1,position,Allele_1,target_chromosome") do |o|
32
32
  options[:snp_file] = o
33
33
  end
34
34
  opts.on("-r", "--reference FASTA", "reference with the genes/contings/marker seuqnece") do |o|
@@ -2,16 +2,16 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
- # stub: bio-polyploid-tools 0.5.2 ruby lib
5
+ # stub: bio-polyploid-tools 0.6.0 ruby lib
6
6
 
7
7
  Gem::Specification.new do |s|
8
8
  s.name = "bio-polyploid-tools"
9
- s.version = "0.5.2"
9
+ s.version = "0.6.0"
10
10
 
11
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
12
12
  s.require_paths = ["lib"]
13
13
  s.authors = ["Ricardo H. Ramirez-Gonzalez"]
14
- s.date = "2014-10-28"
14
+ s.date = "2015-02-15"
15
15
  s.description = "Repository of tools developed in TGAC and Crop Genetics in JIC to work with polyploid wheat"
16
16
  s.email = "ricardo.ramirez-gonzalez@tgac.ac.uk"
17
17
  s.executables = ["bfr.rb", "count_variations.rb", "filter_blat_by_target_coverage.rb", "find_best_blat_hit.rb", "find_best_exonerate.rb", "hexaploid_primers.rb", "homokaryot_primers.rb", "map_markers_to_contigs.rb", "markers_in_region.rb", "polymarker.rb", "snp_position_to_polymarker.rb", "snps_between_bams.rb"]
@@ -81,6 +81,7 @@ Gem::Specification.new do |s|
81
81
  "lib/bio/PolyploidTools/Marker.rb",
82
82
  "lib/bio/PolyploidTools/PrimerRegion.rb",
83
83
  "lib/bio/PolyploidTools/SNP.rb",
84
+ "lib/bio/PolyploidTools/SNPMutant.rb",
84
85
  "lib/bio/PolyploidTools/SNPSequence.rb",
85
86
  "lib/bio/db/exonerate.rb",
86
87
  "lib/bio/db/primer3.rb",
@@ -91,6 +92,8 @@ Gem::Specification.new do |s|
91
92
  "test/data/BS00068396_51_contigs.fa",
92
93
  "test/data/BS00068396_51_exonerate.tab",
93
94
  "test/data/BS00068396_51_genes.txt",
95
+ "test/data/IWGSC_CSS_1AL_scaff_1455974.fa",
96
+ "test/data/IWGSC_CSS_1AL_scaff_1455974_aln_contigs.fa",
94
97
  "test/data/LIB1716.bam",
95
98
  "test/data/LIB1716.bam.bai",
96
99
  "test/data/LIB1719.bam",
@@ -111,6 +114,7 @@ Gem::Specification.new do |s|
111
114
  "test/data/patological_cases5D.csv",
112
115
  "test/data/primer_3_input_header_test",
113
116
  "test/data/short_primer_design_test.csv",
117
+ "test/data/test_from_mutant.csv",
114
118
  "test/data/test_iselect.csv",
115
119
  "test/data/test_iselect_reference.fa",
116
120
  "test/data/test_iselect_reference.fa.fai",
@@ -14,6 +14,7 @@ module Bio::PolyploidTools
14
14
  attr_accessor :genomes_count
15
15
  attr_accessor :primer_3_min_seq_length
16
16
  attr_accessor :chromosome
17
+ attr_accessor :variation_free_region
17
18
 
18
19
  #Format:
19
20
  #Gene_name,Original,SNP_Pos,pos,chromosome
@@ -37,6 +38,7 @@ module Bio::PolyploidTools
37
38
  def initialize
38
39
  @genomes_count = 3 #TODO: if we want to use this with other polyploids, me need to set this as a variable in the main script.
39
40
  @primer_3_min_seq_length = 50
41
+ @variation_free_region = 0
40
42
  end
41
43
 
42
44
  def to_polymarker_sequence(flanking_size)
@@ -260,8 +262,14 @@ module Bio::PolyploidTools
260
262
  sequence = reverse_complement_string(sequence)
261
263
  orientation = "reverse"
262
264
  end
265
+ if @variation_free_region > 0
266
+ check_str = sequence[right+1, @variation_free_region]
267
+ return nil if check_str != check_str.downcase
268
+ end
269
+
263
270
  end
264
271
 
272
+
265
273
  str = "SEQUENCE_ID=#{opts[:name]} #{orientation}\n"
266
274
  str << "SEQUENCE_FORCE_LEFT_END=#{left}\n"
267
275
  str << "SEQUENCE_FORCE_RIGHT_END=#{right}\n" if opts[:right_pos]
@@ -279,8 +287,6 @@ module Bio::PolyploidTools
279
287
  str << "SEQUENCE_FORCE_LEFT_END=#{left}\n"
280
288
  str << "SEQUENCE_TEMPLATE=#{sequence}\n"
281
289
  str << "=\n"
282
- else
283
-
284
290
  end
285
291
 
286
292
  str
@@ -0,0 +1,85 @@
1
+
2
+ require_relative "SNPSequence"
3
+ require 'bio-samtools'
4
+ module Bio::PolyploidTools
5
+ class SNPSequenceException < RuntimeError
6
+ end
7
+
8
+ class SNPMutant < SNPSequence
9
+
10
+ attr_accessor :library, :contig, :chr
11
+ #Format:
12
+ #seqid,library,position,wt_base,mut_base
13
+ #IWGSC_CSS_1AL_scaff_1455974,Kronos2281,127,C,T
14
+ def self.parse(reg_str)
15
+ reg_str.chomp!
16
+ snp = SNPMutant.new
17
+
18
+ arr = reg_str.split(",")
19
+
20
+ throw SNPSequenceException.new "Need five fields to parse, and got #{arr.size} in #{reg_str}" unless arr.size == 5
21
+
22
+ snp.contig, snp.library, snp.position, snp.original, snp.snp = reg_str.split(",")
23
+ snp.position = snp.position.to_i
24
+ snp.gene = "EMPTY"
25
+ begin
26
+ toks = snp.contig.split('_')
27
+ #1AL_1455974_Kronos2281_127C
28
+ #snp.chr = contig.split('_')[2][0,2] #This parses the default from the IWGSC. We may want to make this a lambda
29
+ #snp.chr = toks[2][0,2]
30
+ name = toks[2] + "_" + toks[4] + "_" + snp.library + "_" + snp.position.to_s
31
+ snp.gene = name
32
+ snp.chromosome = toks[2][0,2]
33
+ snp.chr = snp.chromosome
34
+
35
+ rescue Exception => e
36
+ $stderr.puts "WARN: snp.chr couldnt be set, the sequence id to parse was #{snp.contig}. We expect something like: IWGSC_CSS_1AL_scaff_1455974"
37
+ snp.gene = "Error"
38
+ $stderr.puts e
39
+ end
40
+
41
+ snp.exon_list = Hash.new()
42
+ snp.flanking_size=100
43
+ snp
44
+ end
45
+
46
+ def full_sequence=(seq)
47
+ self.template_sequence = seq
48
+ self.sequence_original = self.to_polymarker_sequence(self.flanking_size)
49
+ self.parse_sequence_snp
50
+ end
51
+
52
+ def full_sequence()
53
+ self.template_sequence
54
+ end
55
+
56
+ def chromosome_group
57
+ chr[0]
58
+ end
59
+
60
+ def chromosome_genome
61
+ chr[1]
62
+ end
63
+
64
+ def chromosome_genome
65
+ return chr[3] if chr[3]
66
+ return nil
67
+ end
68
+
69
+ def parse_sequence_snp
70
+ pos = 0
71
+ match_data = /(?<pre>\w*)\[(?<org>[ACGT])\/(?<snp>[ACGT])\](?<pos>\w*)/.match(sequence_original.strip)
72
+ if match_data
73
+ @position = Regexp.last_match(:pre).size + 1
74
+ @original = Regexp.last_match(:org)
75
+ @snp = Regexp.last_match(:snp)
76
+ amb_base = Bio::NucleicAcid.to_IUAPC("#{@original}#{@snp}")
77
+ @template_sequence = "#{Regexp.last_match(:pre)}#{amb_base}#{Regexp.last_match(:pos)}"
78
+
79
+ end
80
+ end
81
+
82
+
83
+
84
+ end
85
+ end
@@ -41,14 +41,14 @@ module Bio::PolyploidTools
41
41
  pos = 0
42
42
  match_data = /(?<pre>\w*)\[(?<org>[ACGT])\/(?<snp>[ACGT])\](?<pos>\w*)/.match(sequence_original.strip)
43
43
  if match_data
44
- @position = Regexp.last_match(:pre).size + 1
45
- @original = Regexp.last_match(:org)
46
- @snp = Regexp.last_match(:snp)
47
-
48
- amb_base = Bio::NucleicAcid.to_IUAPC("#{@original}#{@snp}")
49
-
50
- @template_sequence = "#{Regexp.last_match(:pre)}#{amb_base}#{Regexp.last_match(:pos)}"
51
-
44
+ @position = Regexp.last_match(:pre).size + 1
45
+ @original = Regexp.last_match(:org)
46
+ @snp = Regexp.last_match(:snp)
47
+
48
+ amb_base = Bio::NucleicAcid.to_IUAPC("#{@original}#{@snp}")
49
+
50
+ @template_sequence = "#{Regexp.last_match(:pre)}#{amb_base}#{Regexp.last_match(:pos)}"
51
+
52
52
  end
53
53
  end
54
54
 
@@ -17,18 +17,18 @@ module Bio::DB::Primer3
17
17
  end
18
18
 
19
19
  def self.prepare_input_file(file, opts2={})
20
- opts = {
21
- :primer_product_size_range => "50-150" ,
22
- :primer_max_size => 25 ,
23
- :primer_lib_ambiguity_codes_consensus => 1,
24
- :primer_liberal_base => 1,
25
- :primer_num_return => 5,
26
- :primer_explain_flag => 1,
27
- :primer_thermodynamic_parameters_path => File.expand_path(File.dirname(__FILE__) + '../../../../conf/primer3_config/') + '/'
20
+ opts = {
21
+ :primer_product_size_range => "50-150" ,
22
+ :primer_max_size => 25 ,
23
+ :primer_lib_ambiguity_codes_consensus => 1,
24
+ :primer_liberal_base => 1,
25
+ :primer_num_return => 5,
26
+ :primer_explain_flag => 1,
27
+ :primer_thermodynamic_parameters_path => File.expand_path(File.dirname(__FILE__) + '../../../../conf/primer3_config/') + '/'
28
28
  }.merge(opts2)
29
29
 
30
30
  opts.each do |key,value|
31
- file.puts "#{key.to_s.upcase}=#{value}\n"
31
+ file.puts "#{key.to_s.upcase}=#{value}\n"
32
32
  end
33
33
  # file.puts "="
34
34
  end
@@ -68,7 +68,7 @@ module Bio::DB::Primer3
68
68
  @primers_line_1 = SortedSet.new
69
69
  @primers_line_2 = SortedSet.new
70
70
  @regions = SortedSet.new
71
- @primer3_errors = Set.new
71
+ @primer3_errors = Set.new
72
72
  end
73
73
 
74
74
  def line_2_name
@@ -106,24 +106,23 @@ module Bio::DB::Primer3
106
106
  nil
107
107
  end
108
108
 
109
-
110
- def print_primers
111
- #TODO: Retrieve error messages
109
+ def values
110
+ return @values if @values
112
111
  left_start = 0
113
112
  left_end = 0
114
113
  right_start = 0
115
114
  right_end = 0
116
115
  total_columns_before_messages=17
117
- values = Array.new
118
- #values << "#{gene},,#{template_length},"
119
- values << gene
120
- values << "#{original}#{position}#{snp}"
121
- values << template_length
122
- values << snp_from.chromosome
123
- values << regions.size
124
- values << regions.join("|")
116
+ @values = Array.new
117
+ #@values << "#{gene},,#{template_length},"
118
+ @values << gene
119
+ @values << "#{original}#{position}#{snp}"
120
+ @values << template_length
121
+ @values << snp_from.chromosome
122
+ @values << regions.size
123
+ @values << regions.join("|")
125
124
  if primer3_line_1 and primer3_line_2
126
- values << primer3_line_1.polymorphism
125
+ @values << primer3_line_1.polymorphism
127
126
 
128
127
  #Block that searches both if both pairs have a TM
129
128
  primer_2 = primer3_line_2.left_primer_with_coordinates(primer3_line_1.left_coordinates, primer3_line_1.orientation)
@@ -133,27 +132,27 @@ module Bio::DB::Primer3
133
132
  # $stderr.puts primer_1
134
133
  # $stderr.puts primer_2
135
134
  if primer3_line_1 < primer3_line_2 and primer_2_tm != "NA"
136
- values << primer3_line_1.left_primer
137
- values << primer_2
138
- values << primer3_line_1.right_primer
139
- values << primer3_line_1.type.to_s
140
- values << primer3_line_1.orientation.to_s
141
- values << primer3_line_1.best_pair.left.tm
142
- values << primer_2_tm
143
- values << primer3_line_1.best_pair.right.tm
144
- values << "first"
145
- values << primer3_line_1.best_pair.product_size
135
+ @values << primer3_line_1.left_primer
136
+ @values << primer_2
137
+ @values << primer3_line_1.right_primer
138
+ @values << primer3_line_1.type.to_s
139
+ @values << primer3_line_1.orientation.to_s
140
+ @values << primer3_line_1.best_pair.left.tm
141
+ @values << primer_2_tm
142
+ @values << primer3_line_1.best_pair.right.tm
143
+ @values << "first"
144
+ @values << primer3_line_1.best_pair.product_size
146
145
  elsif primer_1_tm != "NA"
147
- values << primer_1
148
- values << primer3_line_2.left_primer
149
- values << primer3_line_2.right_primer
150
- values << primer3_line_2.type.to_s
151
- values << primer3_line_2.orientation.to_s
152
- values << primer_1_tm
153
- values << primer3_line_2.best_pair.left.tm
154
- values << primer3_line_2.best_pair.right.tm
155
- values << "second"
156
- values << primer3_line_2.best_pair.product_size
146
+ @values << primer_1
147
+ @values << primer3_line_2.left_primer
148
+ @values << primer3_line_2.right_primer
149
+ @values << primer3_line_2.type.to_s
150
+ @values << primer3_line_2.orientation.to_s
151
+ @values << primer_1_tm
152
+ @values << primer3_line_2.best_pair.left.tm
153
+ @values << primer3_line_2.best_pair.right.tm
154
+ @values << "second"
155
+ @values << primer3_line_2.best_pair.product_size
157
156
  else
158
157
 
159
158
  first_candidate = find_primer_pair_first
@@ -172,80 +171,99 @@ module Bio::DB::Primer3
172
171
 
173
172
  if first_candidate and second_candidate and first_candidate < second_candidate
174
173
  #puts "A"
175
- values << first_candidate.left_primer
176
- values << primer_2
177
- values << first_candidate.right_primer
178
- values << first_candidate.type.to_s
179
- values << first_candidate.orientation.to_s
180
- values << first_candidate.best_pair.left.tm
181
- values << primer_2_tm
182
- values << first_candidate.best_pair.right.tm
183
- values << "first"
184
- values << first_candidate.best_pair.product_size
174
+ @values << first_candidate.left_primer
175
+ @values << primer_2
176
+ @values << first_candidate.right_primer
177
+ @values << first_candidate.type.to_s
178
+ @values << first_candidate.orientation.to_s
179
+ @values << first_candidate.best_pair.left.tm
180
+ @values << primer_2_tm
181
+ @values << first_candidate.best_pair.right.tm
182
+ @values << "first"
183
+ @values << first_candidate.best_pair.product_size
185
184
  elsif second_candidate
186
185
  #puts "B"
187
- values << primer_1
188
- values << second_candidate.left_primer
189
- values << second_candidate.right_primer
190
- values << second_candidate.type.to_s
191
- values << second_candidate.orientation.to_s
192
- values << primer_1_tm
193
- values << second_candidate.best_pair.left.tm
194
- values << second_candidate.best_pair.right.tm
195
- values << "second"
196
- values << second_candidate.best_pair.product_size
186
+ @values << primer_1
187
+ @values << second_candidate.left_primer
188
+ @values << second_candidate.right_primer
189
+ @values << second_candidate.type.to_s
190
+ @values << second_candidate.orientation.to_s
191
+ @values << primer_1_tm
192
+ @values << second_candidate.best_pair.left.tm
193
+ @values << second_candidate.best_pair.right.tm
194
+ @values << "second"
195
+ @values << second_candidate.best_pair.product_size
197
196
  elsif first_candidate
198
197
  #puts "C"
199
- values << first_candidate.left_primer
200
- values << primer_2
201
- values << first_candidate.right_primer
202
- values << first_candidate.type.to_s
203
- values << first_candidate.orientation.to_s
204
- values << primer_2_tm
205
- values << first_candidate.best_pair.left.tm
206
- values << first_candidate.best_pair.right.tm
207
- values << "first"
208
- values << first_candidate.best_pair.product_size
209
- # else
210
- # values << ""
198
+ @values << first_candidate.left_primer
199
+ @values << primer_2
200
+ @values << first_candidate.right_primer
201
+ @values << first_candidate.type.to_s
202
+ @values << first_candidate.orientation.to_s
203
+ @values << primer_2_tm
204
+ @values << first_candidate.best_pair.left.tm
205
+ @values << first_candidate.best_pair.right.tm
206
+ @values << "first"
207
+ @values << first_candidate.best_pair.product_size
211
208
  end
212
-
213
209
  end
214
210
 
215
211
  elsif primer3_line_1
216
- values << primer3_line_1.polymorphism
217
- values << primer3_line_1.left_primer
218
- values << primer3_line_1.left_primer_snp(self)
219
- values << primer3_line_1.right_primer
220
- values << primer3_line_1.type.to_s
221
- values << primer3_line_1.orientation.to_s
222
- values << primer3_line_1.best_pair.left.tm
223
- values << "NA"
224
- values << primer3_line_1.best_pair.right.tm
225
-
226
- values << "first+"
227
- values << primer3_line_1.best_pair.product_size
212
+ @values << primer3_line_1.polymorphism
213
+ @values << primer3_line_1.left_primer
214
+ @values << primer3_line_1.left_primer_snp(self)
215
+ @values << primer3_line_1.right_primer
216
+ @values << primer3_line_1.type.to_s
217
+ @values << primer3_line_1.orientation.to_s
218
+ @values << primer3_line_1.best_pair.left.tm
219
+ @values << "NA"
220
+ @values << primer3_line_1.best_pair.right.tm
221
+
222
+ @values << "first+"
223
+ @values << primer3_line_1.best_pair.product_size
228
224
  elsif primer3_line_2
229
- values << primer3_line_2.polymorphism
230
- values << primer3_line_2.left_primer_snp(self)
231
- values << primer3_line_2.left_primer
232
- values << primer3_line_2.right_primer
233
- values << primer3_line_2.type.to_s
234
- values << primer3_line_2.orientation.to_s
235
- values << "NA"
236
- values << primer3_line_2.best_pair.left.tm
237
- values << primer3_line_2.best_pair.right.tm
238
- values << "second+"
239
- values << primer3_line_2.best_pair.product_size
225
+ @values << primer3_line_2.polymorphism
226
+ @values << primer3_line_2.left_primer_snp(self)
227
+ @values << primer3_line_2.left_primer
228
+ @values << primer3_line_2.right_primer
229
+ @values << primer3_line_2.type.to_s
230
+ @values << primer3_line_2.orientation.to_s
231
+ @values << "NA"
232
+ @values << primer3_line_2.best_pair.left.tm
233
+ @values << primer3_line_2.best_pair.right.tm
234
+ @values << "second+"
235
+ @values << primer3_line_2.best_pair.product_size
240
236
 
241
237
  end
242
- if values.size < total_columns_before_messages
243
- values[total_columns_before_messages] = primer3_errors.to_a.join("|")
238
+ if @values.size < total_columns_before_messages
239
+ @values[total_columns_before_messages] = primer3_errors.to_a.join("|")
244
240
  else
245
- values << nil
241
+ @values << nil
246
242
  end
243
+ return @values
244
+ end
245
+
246
+ def print_primers
247
+ self.values.join(",")
248
+ end
249
+
250
+ def found_primers?
251
+ return self.values[7] && self.values[7] != nil
252
+ end
253
+
254
+ def first_primer
255
+ return self.values[7] if self.values[7] && self.values[7] != nil
256
+ return ""
257
+ end
258
+
259
+ def second_primer
260
+ return self.values[8] if self.values[8] && self.values[8] != nil
261
+ return ""
262
+ end
247
263
 
248
- values.join(",")
264
+ def common_primer
265
+ return self.values[9] if self.values[9]&& self.values[9] != nil
266
+ return ""
249
267
  end
250
268
 
251
269
  def self.parse(reg_str)
@@ -273,10 +291,10 @@ module Bio::DB::Primer3
273
291
  def add_record(primer3record)
274
292
  @primer3_errors = Set.new unless @primer3_errors
275
293
  @template_length = primer3record.sequence_template.size
276
- if primer3record.primer_error != nil
277
- primer3_errors << primer3record.primer_error
278
- return
279
- end
294
+ if primer3record.primer_error != nil
295
+ primer3_errors << primer3record.primer_error
296
+ return
297
+ end
280
298
  case
281
299
 
282
300
  when primer3record.line == @line_1
@@ -451,7 +469,7 @@ module Bio::DB::Primer3
451
469
  @scores[:chromosome_semispecific] = 100
452
470
  @scores[:chromosome_nonspecific] = 0
453
471
  @scores[:exon] = 50
454
-
472
+
455
473
  end
456
474
 
457
475
  def snp
@@ -654,7 +672,7 @@ module Bio::DB::Primer3
654
672
 
655
673
  attr_accessor :line_1, :line_2
656
674
  attr_accessor :snp_hash
657
-
675
+
658
676
 
659
677
  def add_snp_file(filename)
660
678
  @snp_hash=Hash.new unless @snp_hash
@@ -696,6 +714,19 @@ module Bio::DB::Primer3
696
714
  end
697
715
  return str
698
716
  end
717
+
718
+ def print_primers_with_tails(tail_a: "GAAGGTCGGAGTCAACGGATT", tail_b: "GAAGGTGACCAAGTTCATGCT")
719
+ str = ""
720
+ snp_hash.each do |k, snp|
721
+ if snp.found_primers?
722
+ str << snp.gene << snp.original << "\t" << tail_a << snp.first_primer << "\n"
723
+ str << snp.gene << snp.snp << "\t" << tail_b << snp.second_primer << "\n"
724
+ str << snp.gene << "\t" << snp.common_primer << "\n"
725
+ end
726
+ end
727
+ return str
728
+ end
729
+
699
730
  end
700
731
  end
701
732