scaffolder 0.4.4 → 0.5.0
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.
- checksums.yaml +15 -0
- data/.gitignore +22 -0
- data/.travis.yml +2 -0
- data/Gemfile +2 -17
- data/README.rdoc +12 -6
- data/Rakefile +12 -23
- data/lib/scaffolder.rb +3 -2
- data/lib/scaffolder/version.rb +5 -0
- data/scaffolder.gemspec +29 -87
- data/spec/helper.rb +8 -0
- data/spec/insert_spec.rb +75 -0
- data/spec/region_spec.rb +148 -0
- data/spec/scaffolder_spec.rb +112 -0
- data/spec/sequences_spec.rb +110 -0
- data/spec/unresolved_spec.rb +17 -0
- metadata +75 -86
- data/test/helper.rb +0 -30
- data/test/test_insert.rb +0 -77
- data/test/test_region.rb +0 -151
- data/test/test_scaffolder.rb +0 -116
- data/test/test_sequence.rb +0 -107
- data/test/test_unresolved.rb +0 -23
checksums.yaml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
---
|
2
|
+
!binary "U0hBMQ==":
|
3
|
+
metadata.gz: !binary |-
|
4
|
+
MGVhOWZjMWJmZjAwY2M0YjliYmM4ZjU0MWEyYjRmYmE4YzU2MmM0Mw==
|
5
|
+
data.tar.gz: !binary |-
|
6
|
+
Njk0ODAzNmJjMmM5YTliYWMwODBiMDhhZDhkNGU1ZWI5Yjc2MzEwMw==
|
7
|
+
!binary "U0hBNTEy":
|
8
|
+
metadata.gz: !binary |-
|
9
|
+
NTVhZThmYzljYjMwYzY2YWU4NmJiNDJmMTkwMTQ5OTQxODQ4ZTYzZTVlNjU4
|
10
|
+
YTQ2NGVmYWEwYWE2NmRkNWU0MWU2MTEyODNjZjkzOGIyOWJkY2E0YzQ1YmZl
|
11
|
+
NTlhYjIyNWZhNTEzYzQwYmE0YzFkYTVhMzFkZWJiNzMzOGI1ZTY=
|
12
|
+
data.tar.gz: !binary |-
|
13
|
+
Y2E0Y2M4NWU2YTY2NGU4MGNhOTZiMjViN2ZhZjJiY2NjNjBjM2ExZmZmYzZh
|
14
|
+
MGUyYzg0Zjk2MzFhNDhjMjhmZDYwYWJhNThkZmFkZjI3YWMzMWE5ZjljNGU5
|
15
|
+
OTdhYzJlYzkwZmQ0MjAwNDQzZmUwMWJkNjk1NzE0NTRkNjg1NmY=
|
data/.gitignore
ADDED
data/Gemfile
CHANGED
@@ -1,17 +1,2 @@
|
|
1
|
-
source "
|
2
|
-
|
3
|
-
group :default do
|
4
|
-
gem "bio", "~> 1.4"
|
5
|
-
end
|
6
|
-
|
7
|
-
group :development do
|
8
|
-
gem "bundler", "~> 1.0"
|
9
|
-
gem "shoulda", "~> 2.11"
|
10
|
-
gem "rspec", "~> 2.4"
|
11
|
-
gem "mocha", "~> 0.9"
|
12
|
-
gem "yard", "~> 0.6"
|
13
|
-
gem "cucumber", "~> 0.9"
|
14
|
-
gem "aruba", "~> 0.2"
|
15
|
-
gem "jeweler", "~> 1.5"
|
16
|
-
gem "mynyml-redgreen", "~> 0.7.1", :require => 'redgreen'
|
17
|
-
end
|
1
|
+
source "https://rubygems.org"
|
2
|
+
gemspec
|
data/README.rdoc
CHANGED
@@ -15,8 +15,12 @@ repeatability.
|
|
15
15
|
|
16
16
|
== Installing
|
17
17
|
|
18
|
-
Ruby and RubyGems are required to use scaffolder. Scaffolder is
|
19
|
-
|
18
|
+
Ruby and RubyGems are required to use scaffolder. Scaffolder is compatible with
|
19
|
+
at least Ruby versions 1.8.7 and 1.9.2. The {last stable version of the
|
20
|
+
RubyGems package manager}[https://rubygems.org/pages/download] is recommended
|
21
|
+
for installing scaffolder.
|
22
|
+
|
23
|
+
Scaffolder is installed on the command line using:
|
20
24
|
|
21
25
|
$ gem install scaffolder
|
22
26
|
|
@@ -27,10 +31,12 @@ getting started with Scaffolder.
|
|
27
31
|
|
28
32
|
== Contact
|
29
33
|
|
30
|
-
Scaffolder was developed by Michael Barton (www.michaelbarton.me.uk).
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
+
Scaffolder was developed by Michael Barton (www.michaelbarton.me.uk). The
|
35
|
+
website for scaffolder is at http://next.gs and a {twitter feed for
|
36
|
+
updates}[http://twitter.com/nxtgs] is available. There is a {Google
|
37
|
+
group}[http://groups.google.com/group/scaffolder] for questions and comments.
|
38
|
+
The source code is available on github[http://github.com/scaffolder]. Bug
|
39
|
+
reports and feature requests may also be made there.
|
34
40
|
|
35
41
|
== Copyright
|
36
42
|
|
data/Rakefile
CHANGED
@@ -7,32 +7,21 @@ rescue Bundler::BundlerError => e
|
|
7
7
|
$stderr.puts "Run `bundle install` to install missing gems"
|
8
8
|
exit e.status_code
|
9
9
|
end
|
10
|
-
require 'rake'
|
11
|
-
|
12
|
-
require 'jeweler'
|
13
|
-
Jeweler::Tasks.new do |gem|
|
14
|
-
gem.name = "scaffolder"
|
15
|
-
gem.homepage = "http://next.gs"
|
16
|
-
gem.license = "MIT"
|
17
|
-
gem.summary = %Q{Genome scaffolding for human beings.}
|
18
|
-
gem.description = %Q{Organise sequence contigs into genome scaffolds using simple human-readable YAML files.}
|
19
|
-
gem.email = "mail@next.gs"
|
20
|
-
gem.authors = ["Michael Barton"]
|
21
|
-
gem.test_files = Dir['test/**/*.rb']
|
22
|
-
end
|
23
|
-
Jeweler::RubygemsDotOrgTasks.new
|
24
|
-
|
25
|
-
require 'rake/testtask'
|
26
|
-
Rake::TestTask.new(:test) do |test|
|
27
|
-
test.libs << 'lib' << 'test'
|
28
|
-
test.pattern = 'test/**/test_*.rb'
|
29
|
-
test.verbose = true
|
30
|
-
end
|
31
10
|
|
11
|
+
require 'rake/dsl_definition'
|
12
|
+
require 'rspec/core'
|
13
|
+
require 'rspec/core/rake_task'
|
32
14
|
require 'cucumber/rake/task'
|
33
|
-
|
15
|
+
|
16
|
+
Bundler::GemHelper.install_tasks
|
34
17
|
|
35
18
|
require 'yard'
|
36
19
|
YARD::Rake::YardocTask.new
|
37
20
|
|
38
|
-
|
21
|
+
RSpec::Core::RakeTask.new(:spec) do |spec|
|
22
|
+
spec.pattern = FileList['spec/**/*_spec.rb']
|
23
|
+
end
|
24
|
+
|
25
|
+
Cucumber::Rake::Task.new(:features)
|
26
|
+
|
27
|
+
task :default => :spec
|
data/lib/scaffolder.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
|
-
require '
|
1
|
+
require 'scaffolder/version'
|
2
|
+
|
2
3
|
require 'bio'
|
3
4
|
|
4
5
|
# == Quick start
|
@@ -148,7 +149,7 @@ require 'bio'
|
|
148
149
|
# Inserts with overlapping *open* and *close* regions in the same sequence will
|
149
150
|
# cause unexpected behaviour and should be avoided.
|
150
151
|
#
|
151
|
-
class Scaffolder
|
152
|
+
class Scaffolder
|
152
153
|
require 'scaffolder/errors'
|
153
154
|
require 'scaffolder/region'
|
154
155
|
|
data/scaffolder.gemspec
CHANGED
@@ -1,93 +1,35 @@
|
|
1
|
-
#
|
2
|
-
|
3
|
-
|
4
|
-
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'scaffolder/version'
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
|
-
s.name
|
8
|
-
s.version
|
7
|
+
s.name = "scaffolder"
|
8
|
+
s.version = Scaffolder::VERSION
|
9
|
+
s.platform = Gem::Platform::RUBY
|
10
|
+
s.authors = ["Michael Barton"]
|
11
|
+
s.email = %q{mail@next.gs}
|
12
|
+
s.homepage = "http://next.gs"
|
13
|
+
s.summary = %Q{Build genome output files}
|
14
|
+
s.description = %Q{Turns scaffolded contigs and annotations into a genome.}
|
15
|
+
s.license = "MIT"
|
9
16
|
|
10
|
-
s.required_rubygems_version =
|
11
|
-
s.
|
12
|
-
s.date = %q{2011-08-11}
|
13
|
-
s.description = %q{Organise sequence contigs into genome scaffolds using simple human-readable YAML files.}
|
14
|
-
s.email = %q{mail@next.gs}
|
15
|
-
s.extra_rdoc_files = [
|
16
|
-
"LICENSE",
|
17
|
-
"README.rdoc"
|
18
|
-
]
|
19
|
-
s.files = [
|
20
|
-
".document",
|
21
|
-
".travis.yml",
|
22
|
-
"Gemfile",
|
23
|
-
"LICENSE",
|
24
|
-
"README.rdoc",
|
25
|
-
"Rakefile",
|
26
|
-
"VERSION",
|
27
|
-
"cucumber.yml",
|
28
|
-
"features/insert.feature",
|
29
|
-
"features/sequence.feature",
|
30
|
-
"features/step_definitions/scaffolder_steps.rb",
|
31
|
-
"features/support/env.rb",
|
32
|
-
"lib/scaffolder.rb",
|
33
|
-
"lib/scaffolder/errors.rb",
|
34
|
-
"lib/scaffolder/region.rb",
|
35
|
-
"lib/scaffolder/region/insert.rb",
|
36
|
-
"lib/scaffolder/region/sequence.rb",
|
37
|
-
"lib/scaffolder/region/unresolved.rb",
|
38
|
-
"scaffolder.gemspec",
|
39
|
-
"test/helper.rb",
|
40
|
-
"test/test_insert.rb",
|
41
|
-
"test/test_region.rb",
|
42
|
-
"test/test_scaffolder.rb",
|
43
|
-
"test/test_sequence.rb",
|
44
|
-
"test/test_unresolved.rb",
|
45
|
-
"yard/attribute_handler.rb"
|
46
|
-
]
|
47
|
-
s.homepage = %q{http://next.gs}
|
48
|
-
s.licenses = ["MIT"]
|
49
|
-
s.require_paths = ["lib"]
|
50
|
-
s.rubygems_version = %q{1.6.2}
|
51
|
-
s.summary = %q{Genome scaffolding for human beings.}
|
52
|
-
s.test_files = ["test/helper.rb", "test/test_insert.rb", "test/test_region.rb", "test/test_scaffolder.rb", "test/test_sequence.rb", "test/test_unresolved.rb"]
|
17
|
+
s.required_rubygems_version = ">= 1.8.0"
|
18
|
+
s.rubyforge_project = "scaffolder"
|
53
19
|
|
54
|
-
|
55
|
-
|
20
|
+
s.add_dependency "rake" , "~> 10.1.0"
|
21
|
+
s.add_dependency "bundler", "~> 1.3.0"
|
22
|
+
s.add_dependency "bio", "~> 1.4.0"
|
56
23
|
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
s.add_development_dependency(%q<aruba>, ["~> 0.2"])
|
66
|
-
s.add_development_dependency(%q<jeweler>, ["~> 1.5"])
|
67
|
-
s.add_development_dependency(%q<mynyml-redgreen>, ["~> 0.7.1"])
|
68
|
-
else
|
69
|
-
s.add_dependency(%q<bio>, ["~> 1.4"])
|
70
|
-
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
71
|
-
s.add_dependency(%q<shoulda>, ["~> 2.11"])
|
72
|
-
s.add_dependency(%q<rspec>, ["~> 2.4"])
|
73
|
-
s.add_dependency(%q<mocha>, ["~> 0.9"])
|
74
|
-
s.add_dependency(%q<yard>, ["~> 0.6"])
|
75
|
-
s.add_dependency(%q<cucumber>, ["~> 0.9"])
|
76
|
-
s.add_dependency(%q<aruba>, ["~> 0.2"])
|
77
|
-
s.add_dependency(%q<jeweler>, ["~> 1.5"])
|
78
|
-
s.add_dependency(%q<mynyml-redgreen>, ["~> 0.7.1"])
|
79
|
-
end
|
80
|
-
else
|
81
|
-
s.add_dependency(%q<bio>, ["~> 1.4"])
|
82
|
-
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
83
|
-
s.add_dependency(%q<shoulda>, ["~> 2.11"])
|
84
|
-
s.add_dependency(%q<rspec>, ["~> 2.4"])
|
85
|
-
s.add_dependency(%q<mocha>, ["~> 0.9"])
|
86
|
-
s.add_dependency(%q<yard>, ["~> 0.6"])
|
87
|
-
s.add_dependency(%q<cucumber>, ["~> 0.9"])
|
88
|
-
s.add_dependency(%q<aruba>, ["~> 0.2"])
|
89
|
-
s.add_dependency(%q<jeweler>, ["~> 1.5"])
|
90
|
-
s.add_dependency(%q<mynyml-redgreen>, ["~> 0.7.1"])
|
91
|
-
end
|
92
|
-
end
|
24
|
+
# Specs
|
25
|
+
s.add_development_dependency "rspec", "~> 2.14.0"
|
26
|
+
s.add_development_dependency "mocha", "~> 0.14.0"
|
27
|
+
s.add_development_dependency "yard", "~> 0.8.0"
|
28
|
+
|
29
|
+
# Features
|
30
|
+
s.add_development_dependency "cucumber", "~> 1.3.0"
|
31
|
+
s.add_development_dependency "aruba", "~> 0.5.3"
|
93
32
|
|
33
|
+
s.files = `git ls-files`.split("\n")
|
34
|
+
s.require_path = 'lib'
|
35
|
+
end
|
data/spec/helper.rb
ADDED
data/spec/insert_spec.rb
ADDED
@@ -0,0 +1,75 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
describe Scaffolder::Region::Insert do
|
4
|
+
|
5
|
+
describe "attributes" do
|
6
|
+
|
7
|
+
its(:class){ should respond_to(:attribute)}
|
8
|
+
it{ should respond_to :source, :open, :close}
|
9
|
+
|
10
|
+
let(:length){ 15 }
|
11
|
+
|
12
|
+
before do
|
13
|
+
subject.raw_sequence('N' * length)
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should return open plus sequence length as default close" do
|
17
|
+
subject.open 5
|
18
|
+
subject.close.should == (subject.open + length - 1)
|
19
|
+
end
|
20
|
+
|
21
|
+
it "should return close minus sequence length as default open" do
|
22
|
+
subject.close 20
|
23
|
+
subject.open.should == (subject.close - length - 1)
|
24
|
+
end
|
25
|
+
|
26
|
+
it "should include the insert position" do
|
27
|
+
subject.open 5
|
28
|
+
subject.close 10
|
29
|
+
subject.position.should == (4..9)
|
30
|
+
end
|
31
|
+
|
32
|
+
it "should throw an error when neither open or close are provided" do
|
33
|
+
lambda{subject.position}.should raise_error(Scaffolder::Errors::CoordinateError)
|
34
|
+
end
|
35
|
+
|
36
|
+
end
|
37
|
+
|
38
|
+
describe "#size_diff" do
|
39
|
+
|
40
|
+
before do
|
41
|
+
subject.open 3
|
42
|
+
subject.close 5
|
43
|
+
end
|
44
|
+
|
45
|
+
it "should return a negative diff for a sequence smaller than insert site" do
|
46
|
+
subject.raw_sequence 'TT'
|
47
|
+
subject.size_diff.should == -1
|
48
|
+
end
|
49
|
+
|
50
|
+
it "should return 0 for a sequence equal to the insert site" do
|
51
|
+
subject.raw_sequence 'TTT'
|
52
|
+
subject.size_diff.should == 0
|
53
|
+
end
|
54
|
+
|
55
|
+
it "should return a positive diff for a sequence larger than insert site" do
|
56
|
+
subject.raw_sequence 'TTTT'
|
57
|
+
subject.size_diff.should == 1
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
61
|
+
|
62
|
+
it "should be comparable by close position" do
|
63
|
+
a = subject
|
64
|
+
a.close 1
|
65
|
+
|
66
|
+
b = subject.clone
|
67
|
+
b.close 2
|
68
|
+
|
69
|
+
c = subject.clone
|
70
|
+
c.close 3
|
71
|
+
|
72
|
+
[c,a,b].sort.should == [a,b,c]
|
73
|
+
end
|
74
|
+
|
75
|
+
end
|
data/spec/region_spec.rb
ADDED
@@ -0,0 +1,148 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
describe Scaffolder::Region do
|
4
|
+
|
5
|
+
describe "adding instance methods with attribute method" do
|
6
|
+
|
7
|
+
let(:attr){ :some_attribute }
|
8
|
+
|
9
|
+
it "should create a single accessor attribute" do
|
10
|
+
Scaffolder::Region.attribute attr
|
11
|
+
methods = Scaffolder::Region.instance_methods.map{|m| m.to_s}
|
12
|
+
expect(methods).to include(attr.to_s)
|
13
|
+
end
|
14
|
+
|
15
|
+
it "should return nil until attribute value is stored" do
|
16
|
+
Scaffolder::Region.attribute attr
|
17
|
+
region = Scaffolder::Region.new
|
18
|
+
region.send(attr).should be_nil
|
19
|
+
region.send(attr,5)
|
20
|
+
region.send(attr).should == 5
|
21
|
+
end
|
22
|
+
|
23
|
+
it "should allow specification of default value" do
|
24
|
+
Scaffolder::Region.attribute attr, :default => 1
|
25
|
+
region = Scaffolder::Region.new
|
26
|
+
region.send(attr).should == 1
|
27
|
+
region.send(attr,5)
|
28
|
+
region.send(attr).should == 5
|
29
|
+
end
|
30
|
+
|
31
|
+
it "should allow specification of default value using a block" do
|
32
|
+
Scaffolder::Region.attribute attr, :default => lambda{|s| s.entry_type }
|
33
|
+
region = Scaffolder::Region.new
|
34
|
+
region.send(attr).should == region.entry_type
|
35
|
+
region.send(attr,5)
|
36
|
+
region.send(attr).should == 5
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
describe "passing the yaml hash to the generate method" do
|
42
|
+
|
43
|
+
let(:tags) do
|
44
|
+
{'one' => 1, 'two' => 2}
|
45
|
+
end
|
46
|
+
|
47
|
+
before do
|
48
|
+
Scaffolder::Region.attribute(:one)
|
49
|
+
Scaffolder::Region.attribute(:two)
|
50
|
+
end
|
51
|
+
|
52
|
+
it "should should call each tag in the hash as a method to store the value" do
|
53
|
+
Scaffolder::Region.any_instance.expects(:one).with(1)
|
54
|
+
Scaffolder::Region.any_instance.expects(:two).with(2)
|
55
|
+
Scaffolder::Region.generate(tags)
|
56
|
+
end
|
57
|
+
|
58
|
+
it "should return an instantiated region object" do
|
59
|
+
region = Scaffolder::Region.generate(tags)
|
60
|
+
region.one.should == 1
|
61
|
+
region.two.should == 2
|
62
|
+
end
|
63
|
+
|
64
|
+
it "should throw UnknownAttributeError for an unknown attribute" do
|
65
|
+
lambda{ Scaffolder::Region.generate({:three => 3}) }.should \
|
66
|
+
raise_error(Scaffolder::Errors::UnknownAttributeError)
|
67
|
+
end
|
68
|
+
|
69
|
+
end
|
70
|
+
|
71
|
+
context "attributes" do
|
72
|
+
|
73
|
+
it{ should respond_to :start, :stop, :reverse, :raw_sequence }
|
74
|
+
|
75
|
+
it "should return the class name as the entry type" do
|
76
|
+
Scaffolder::Region::NewRegion = Class.new(Scaffolder::Region)
|
77
|
+
Scaffolder::Region::NewRegion.new.entry_type.should == :newregion
|
78
|
+
end
|
79
|
+
|
80
|
+
it "should return 1 as default value for start attribute" do
|
81
|
+
sequence = Scaffolder::Region.new
|
82
|
+
sequence.start.should == 1
|
83
|
+
end
|
84
|
+
|
85
|
+
it "should return #raw_sequence length as default value for stop attribute" do
|
86
|
+
length = 5
|
87
|
+
subject.raw_sequence('N' * length)
|
88
|
+
subject.stop.should == length
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
|
93
|
+
describe "generating the processed sequence" do
|
94
|
+
|
95
|
+
[:sequence_hook, :raw_sequence].each do |method|
|
96
|
+
|
97
|
+
context "using the #{method} method" do
|
98
|
+
|
99
|
+
let(:region) do
|
100
|
+
# Test class to prevent interference with other tests
|
101
|
+
s = Class.new(Scaffolder::Region).new
|
102
|
+
s.class.send(:define_method,method,lambda{'ATGCCAGATAACTGACTAGCATG'})
|
103
|
+
s
|
104
|
+
end
|
105
|
+
|
106
|
+
it "should return the sequence when no other options are passed" do
|
107
|
+
region.sequence.should == 'ATGCCAGATAACTGACTAGCATG'
|
108
|
+
end
|
109
|
+
|
110
|
+
it "should reverse complement sequence when passed the reverse option" do
|
111
|
+
region.reverse true
|
112
|
+
region.sequence.should == 'CATGCTAGTCAGTTATCTGGCAT'
|
113
|
+
end
|
114
|
+
|
115
|
+
it "should create subsequence when passed sequence coordinates" do
|
116
|
+
region.start 5
|
117
|
+
region.stop 20
|
118
|
+
region.sequence.should == 'CAGATAACTGACTAGC'
|
119
|
+
end
|
120
|
+
|
121
|
+
it "should raise a CoordinateError when start is less than 1" do
|
122
|
+
region.start 0
|
123
|
+
lambda{ region.sequence }.should raise_error(Scaffolder::Errors::CoordinateError)
|
124
|
+
end
|
125
|
+
|
126
|
+
it "should raise a CoordinateError when stop is greater than sequence " do
|
127
|
+
region.stop 24
|
128
|
+
lambda{region.sequence}.should raise_error(Scaffolder::Errors::CoordinateError)
|
129
|
+
end
|
130
|
+
|
131
|
+
it "should raise a CoordinateError when stop is greater than start " do
|
132
|
+
region.start 6
|
133
|
+
region.stop 5
|
134
|
+
lambda{ region.sequence }.should raise_error(Scaffolder::Errors::CoordinateError)
|
135
|
+
end
|
136
|
+
|
137
|
+
end
|
138
|
+
|
139
|
+
end
|
140
|
+
|
141
|
+
end
|
142
|
+
|
143
|
+
it "should instantiate return corresponding region subclass when requested" do
|
144
|
+
Scaffolder::Region::Type = Class.new
|
145
|
+
Scaffolder::Region['type'].should == Scaffolder::Region::Type
|
146
|
+
end
|
147
|
+
|
148
|
+
end
|