surveyor 1.1.0 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGELOG.md +19 -1
- data/Gemfile.rails_version +2 -2
- data/app/views/partials/_answer.html.haml +1 -0
- data/app/views/partials/_question_group.html.haml +3 -1
- data/app/views/surveyor/export.json.rabl +4 -1
- data/features/export_to_json.feature +5 -1
- data/features/step_definitions/parser_steps.rb +4 -1
- data/features/step_definitions/surveyor_steps.rb +20 -0
- data/features/step_definitions/web_steps.rb +4 -0
- data/features/surveyor.feature +87 -1
- data/features/surveyor_dependencies.feature +59 -0
- data/features/surveyor_parser.feature +29 -0
- data/lib/surveyor/common.rb +17 -0
- data/lib/surveyor/helpers/surveyor_helper_methods.rb +8 -2
- data/lib/surveyor/models/response_set_methods.rb +2 -4
- data/lib/surveyor/models/survey_methods.rb +20 -11
- data/lib/surveyor/parser.rb +2 -2
- data/lib/surveyor/redcap_parser.rb +1 -3
- data/lib/surveyor/render_text.rb +8 -4
- data/lib/surveyor/surveyor_controller_methods.rb +6 -0
- data/lib/surveyor/version.rb +1 -1
- data/spec/controllers/surveyor_controller_spec.rb +80 -0
- data/spec/helpers/surveyor_helper_spec.rb +4 -4
- metadata +275 -265
data/CHANGELOG.md
CHANGED
@@ -1,12 +1,30 @@
|
|
1
1
|
History for Surveyor
|
2
2
|
====================
|
3
3
|
|
4
|
+
1.2.0
|
5
|
+
-----
|
6
|
+
|
7
|
+
### Features
|
8
|
+
|
9
|
+
- Allow rendering of simple hash contexts with Mustache (#296)
|
10
|
+
- Allow configuration of question numbering (#136)
|
11
|
+
- Allow references to question_ and answer_ in dependency conditions (#345)
|
12
|
+
|
13
|
+
### Fixes
|
14
|
+
|
15
|
+
- Surveyor will never require 'fastercsv' on Ruby 1.9. (#381)
|
16
|
+
- Add question_groups/question/answer/reference_identifier to JSON
|
17
|
+
serialization for Survey. (#390)
|
18
|
+
- Evaluate dependencies even when the last response is removed (#362, #215)
|
19
|
+
- Add answer help text (#373)
|
20
|
+
- SurveyorController#export now renders 404 when surveys are not found (#391)
|
21
|
+
|
4
22
|
1.1.0
|
5
23
|
-----
|
6
24
|
|
7
25
|
### Features
|
8
26
|
|
9
|
-
- Breaking change: Question#is_mandatory => false by default. For those who found it useful to have
|
27
|
+
- Breaking change: Question#is_mandatory => false by default. For those who found it useful to have
|
10
28
|
all questions mandatory, the parser accepts `:default_mandatory => true` as an argument to the survey.
|
11
29
|
|
12
30
|
### Fixes
|
data/Gemfile.rails_version
CHANGED
@@ -8,11 +8,11 @@ if ENV['RAILS_VERSION']
|
|
8
8
|
when /3.1$/
|
9
9
|
gem 'rails', '~> 3.1.0'
|
10
10
|
# A JS runtime is required for Rails 3.1+
|
11
|
-
gem 'therubyracer'
|
11
|
+
gem 'therubyracer', '~> 0.10.2'
|
12
12
|
when /3.2$/
|
13
13
|
gem 'rails', '~> 3.2.0'
|
14
14
|
# A JS runtime is required for Rails 3.1+
|
15
|
-
gem 'therubyracer'
|
15
|
+
gem 'therubyracer', '~> 0.10.2'
|
16
16
|
else
|
17
17
|
fail "Unknown Rails version #{ENV['RAILS_VERSION']}"
|
18
18
|
end
|
@@ -4,6 +4,7 @@
|
|
4
4
|
- i = response_idx(q.pick != "one") # argument will be false (don't increment i) if we're on radio buttons
|
5
5
|
- disabled = defined?(disableFlag) ? disableFlag : false
|
6
6
|
= f.semantic_fields_for i, r do |ff|
|
7
|
+
%span.help= render_help_text(a, @render_context) unless g && g.display_type == "grid"
|
7
8
|
= ff.input :question_id, :as => :quiet unless q.pick == "one" # don't repeat question_id if we're on radio buttons
|
8
9
|
= ff.input :api_id, :as => :quiet unless q.pick == "one"
|
9
10
|
= ff.input :response_group, :value => rg, :as => :quiet if q.pick != "one" && g && g.display_type == "repeater"
|
@@ -15,7 +15,9 @@
|
|
15
15
|
%tr
|
16
16
|
%th
|
17
17
|
- ten_questions.first.answers.each do |a|
|
18
|
-
%th
|
18
|
+
%th
|
19
|
+
=a_text(a)
|
20
|
+
%span.help= render_help_text(a, @render_context)
|
19
21
|
%th
|
20
22
|
- ten_questions.each_with_index do |q, i|
|
21
23
|
%tr{:id => "q_#{q.id}", :class => "q_#{renderer} #{q.css_class(@response_set)}"}
|
@@ -51,6 +51,7 @@ child :sections => :sections do
|
|
51
51
|
node(:post_text, :if => lambda { |q| !q.split_text(:post).blank? }){ |q| q.split_text(:post) }
|
52
52
|
node(:help_text, :if => lambda { |q| !q.help_text.blank? }){ |q| q.help_text }
|
53
53
|
node(:reference_identifier, :if => lambda { |q| !q.reference_identifier.blank? }){ |q| q.reference_identifier }
|
54
|
+
node(:data_export_identifier, :if => lambda { |q| !q.data_export_identifier.blank? }){ |q| q.data_export_identifier }
|
54
55
|
node(:type, :if => lambda { |q| q.display_type != "default" }){ |q| q.display_type }
|
55
56
|
node(:pick, :if => lambda { |q| q.pick != "none" }){ |q| q.pick }
|
56
57
|
|
@@ -61,6 +62,8 @@ child :sections => :sections do
|
|
61
62
|
node(:text){ |a| a.split_or_hidden_text(:pre) }
|
62
63
|
node(:post_text, :if => lambda { |a| !a.split_or_hidden_text(:post).blank? }){ |a| a.split_or_hidden_text(:post) }
|
63
64
|
node(:type, :if => lambda { |a| a.response_class != "answer" }){ |a| a.response_class }
|
65
|
+
node(:reference_identifier, :if => lambda { |a| !a.reference_identifier.blank? }){ |a| a.reference_identifier }
|
66
|
+
node(:data_export_identifier, :if => lambda { |a| !a.data_export_identifier.blank? }){ |a| a.data_export_identifier }
|
64
67
|
end
|
65
68
|
|
66
69
|
child :dependency, :if => lambda { |q| q.dependency } do
|
@@ -75,4 +78,4 @@ child :sections => :sections do
|
|
75
78
|
end
|
76
79
|
end
|
77
80
|
|
78
|
-
end
|
81
|
+
end
|
@@ -241,4 +241,8 @@ Feature: Survey export
|
|
241
241
|
And I export the response set
|
242
242
|
Then the JSON at "responses" should have 1 entry
|
243
243
|
And the JSON response at "responses/0/value" should be "blueish"
|
244
|
-
And the JSON response at "responses/0/answer_id" should correspond to an answer with text "most favorite color"
|
244
|
+
And the JSON response at "responses/0/answer_id" should correspond to an answer with text "most favorite color"
|
245
|
+
|
246
|
+
Scenario: Exporting non-existent surveys
|
247
|
+
When I visit "/surveys/simple-json.json"
|
248
|
+
Then I should get a "404" response
|
@@ -50,8 +50,11 @@ Then /^there should be (\d+) question(?:s?) with:$/ do |x, table|
|
|
50
50
|
table.hashes.each do |hash|
|
51
51
|
hash["reference_identifier"] = nil if hash["reference_identifier"] == "nil"
|
52
52
|
hash["custom_class"] = nil if hash["custom_class"] == "nil"
|
53
|
-
|
53
|
+
if hash.has_key?("is_mandatory")
|
54
|
+
hash["is_mandatory"] = (hash["is_mandatory"] == "true" ? true : (hash["is_mandatory"] == "false" ? false : hash["is_mandatory"]))
|
55
|
+
end
|
54
56
|
result = Question.find(:first, :conditions => hash)
|
57
|
+
puts hash if result.nil?
|
55
58
|
result.should_not be_nil
|
56
59
|
end
|
57
60
|
end
|
@@ -225,6 +225,26 @@ Given /^I have survey context of "(.*)"$/ do |context|
|
|
225
225
|
end
|
226
226
|
end
|
227
227
|
|
228
|
+
Given /^I have a simple hash context$/ do
|
229
|
+
class SurveyorController < ApplicationController
|
230
|
+
def render_context
|
231
|
+
{:name => "Moses", :site => "Northwestern"}
|
232
|
+
end
|
233
|
+
end
|
234
|
+
end
|
235
|
+
|
236
|
+
Given /^I replace question numbers with letters$/ do
|
237
|
+
module SurveyorHelper
|
238
|
+
include Surveyor::Helpers::SurveyorHelperMethods
|
239
|
+
def next_question_number(question)
|
240
|
+
@letters ||= ("A".."Z").to_a
|
241
|
+
@n ||= 25
|
242
|
+
"<span class='qnum'>#{@letters[(@n += 1)%26]}. </span>"
|
243
|
+
end
|
244
|
+
end
|
245
|
+
end
|
246
|
+
|
247
|
+
|
228
248
|
## Various input elements
|
229
249
|
|
230
250
|
Then /^I should see (\d+) textareas on the page$/ do |i|
|
data/features/surveyor.feature
CHANGED
@@ -334,7 +334,7 @@ Feature: Survey creation
|
|
334
334
|
|
335
335
|
|
336
336
|
# Issue 259 - substitution of the text with Mustache
|
337
|
-
@javascript
|
337
|
+
@javascript @mustache
|
338
338
|
Scenario: Creating a question with an mustache syntax
|
339
339
|
Given I have survey context of "FakeMustacheContext"
|
340
340
|
Given I parse
|
@@ -364,6 +364,36 @@ Feature: Survey creation
|
|
364
364
|
And I should see "Santa Claus lives on South Pole"
|
365
365
|
And I should see "Santa Claus doesn't exist"
|
366
366
|
|
367
|
+
# Issue 296 - Mustache rendering doesn't work with simple hash contexts
|
368
|
+
@javascript @mustache
|
369
|
+
Scenario: Creating a question with an mustache syntax
|
370
|
+
Given I have a simple hash context
|
371
|
+
Given I parse
|
372
|
+
"""
|
373
|
+
survey "Overall info" do
|
374
|
+
section "Group of questions" do
|
375
|
+
group "Information on {{name}}?", :help_text => "Answer all you know on {{name}}" do
|
376
|
+
label "{{name}} does not work for {{site}}!", :help_text => "Make sure you sure {{name}} doesn't work for {{site}}"
|
377
|
+
|
378
|
+
q "Where does {{name}} live?", :pick => :one,
|
379
|
+
:help_text => "If you don't know where {{name}} lives, skip the question"
|
380
|
+
a "{{name}} lives on North Pole"
|
381
|
+
a "{{name}} lives on South Pole"
|
382
|
+
a "{{name}} doesn't exist"
|
383
|
+
end
|
384
|
+
end
|
385
|
+
end
|
386
|
+
"""
|
387
|
+
When I start the "Overall info" survey
|
388
|
+
Then I should see "Information on Moses"
|
389
|
+
And I should see "Answer all you know on Moses"
|
390
|
+
And I should see "Moses does not work for Northwestern!"
|
391
|
+
And I should see "Make sure you sure Moses doesn't work for Northwestern"
|
392
|
+
And I should see "Where does Moses live?"
|
393
|
+
And I should see "If you don't know where Moses lives, skip the question"
|
394
|
+
And I should see "Moses lives on North Pole"
|
395
|
+
And I should see "Moses lives on South Pole"
|
396
|
+
And I should see "Moses doesn't exist"
|
367
397
|
|
368
398
|
Scenario: Creating and saving grids
|
369
399
|
Given I parse
|
@@ -691,3 +721,59 @@ Feature: Survey creation
|
|
691
721
|
And I should see "1) What is your favorite number?"
|
692
722
|
And I should not see "What is your name?"
|
693
723
|
|
724
|
+
@numbers
|
725
|
+
Scenario: hidden numbers
|
726
|
+
Given I parse
|
727
|
+
"""
|
728
|
+
survey "Alpha" do
|
729
|
+
section "A-C" do
|
730
|
+
q "Aligator"
|
731
|
+
q "Barber"
|
732
|
+
q "Camel"
|
733
|
+
end
|
734
|
+
end
|
735
|
+
"""
|
736
|
+
And I replace question numbers with letters
|
737
|
+
When I start the "Alpha" survey
|
738
|
+
Then I should see "A. Aligator"
|
739
|
+
And I should see "B. Barber"
|
740
|
+
And I should see "C. Camel"
|
741
|
+
|
742
|
+
Scenario: help text
|
743
|
+
Given I parse
|
744
|
+
"""
|
745
|
+
survey "Help!" do
|
746
|
+
section "Songs" do
|
747
|
+
q "Do you need anybody?", :pick => :one, :help_text => "select one of the following"
|
748
|
+
a "I need somebody to love", :help_text => "like The Beatles"
|
749
|
+
a "I am a rock, I am an island", :help_text => "like Simon and Garfunkel"
|
750
|
+
|
751
|
+
grid "How would these artists respond to 'Do you need anybody?'", :help_text => "in your opinion" do
|
752
|
+
a "Yes", :help_text => "would say yes"
|
753
|
+
a "No", :help_text => "would say no"
|
754
|
+
q "Bobby Darrin", :pick => :one
|
755
|
+
q "Kurt Cobain", :pick => :one
|
756
|
+
q "Ella Fitzgerald", :pick => :one
|
757
|
+
q "Kanye West", :pick => :one
|
758
|
+
end
|
759
|
+
|
760
|
+
repeater "Over and over" do
|
761
|
+
q "Row row row your boat", :pick => :any, :help_text => "the 1st part of a round"
|
762
|
+
a "gently down the stream", :help_text => "the 2nd part of a round"
|
763
|
+
a "merrily merrily merrily merrily", :help_text => "the 3rd part of a round"
|
764
|
+
a "life is but a dream", :help_text => "the 4th part of a round"
|
765
|
+
end
|
766
|
+
end
|
767
|
+
end
|
768
|
+
"""
|
769
|
+
When I start the "Help!" survey
|
770
|
+
Then I should see "select one of the following"
|
771
|
+
And I should see "like The Beatles"
|
772
|
+
And I should see "like Simon and Garfunkel"
|
773
|
+
And I should see "in your opinion"
|
774
|
+
And I should see "would say yes"
|
775
|
+
And I should see "would say no"
|
776
|
+
And I should see "the 1st part of a round"
|
777
|
+
And I should see "the 2nd part of a round"
|
778
|
+
And I should see "the 3rd part of a round"
|
779
|
+
And I should see "the 4th part of a round"
|
@@ -361,3 +361,62 @@ Feature: Survey dependencies
|
|
361
361
|
When I check "Once for you"
|
362
362
|
Then the element "#q_3" should not be hidden
|
363
363
|
And the element "#q_2" should be hidden
|
364
|
+
|
365
|
+
@javascript
|
366
|
+
Scenario: Dependency evaluation when the last response is removed
|
367
|
+
Given I parse
|
368
|
+
"""
|
369
|
+
survey "Heating" do
|
370
|
+
section "Basics" do
|
371
|
+
q_heating_1 "How do you heat your home?", :pick => :any
|
372
|
+
a_1 "Forced air"
|
373
|
+
a_2 "Radiators"
|
374
|
+
a_3 "Oven"
|
375
|
+
a_4 "Passive"
|
376
|
+
|
377
|
+
q_heating_2 "How much does it cost to run your non-passive heating solutions?"
|
378
|
+
dependency :rule => "A"
|
379
|
+
condition_A :q_heating_1, "==", :a_1
|
380
|
+
a_1 "$", :float
|
381
|
+
end
|
382
|
+
end
|
383
|
+
"""
|
384
|
+
When I go to the surveys page
|
385
|
+
And I start the "Heating" survey
|
386
|
+
Then the question "How much does it cost to run your non-passive heating solutions?" should be hidden
|
387
|
+
And I check "Forced air"
|
388
|
+
Then the question "How much does it cost to run your non-passive heating solutions?" should be triggered
|
389
|
+
And I uncheck "Forced air"
|
390
|
+
Then the question "How much does it cost to run your non-passive heating solutions?" should be hidden
|
391
|
+
|
392
|
+
@javascript @focus
|
393
|
+
Scenario: Dependency evaluation within groups
|
394
|
+
Given I parse
|
395
|
+
"""
|
396
|
+
survey "Body" do
|
397
|
+
section "Joints" do
|
398
|
+
group "Muscle" do
|
399
|
+
q_muscles_joints_bones "Muscles, Joints, Bones", :pick => :any, :data_export_identifier => "muscles_joints_bones"
|
400
|
+
a_1 "Weakness"
|
401
|
+
a_2 "Arthritis"
|
402
|
+
a_3 "Cane/Walker"
|
403
|
+
a_4 "Morning stiffness"
|
404
|
+
a_5 "Joint pain"
|
405
|
+
a_6 "Muscle tenderness"
|
406
|
+
a_7 :other
|
407
|
+
|
408
|
+
q_muscles_joints_bones_other "Explain", :data_export_identifier => "muscles_joints_bones_other"
|
409
|
+
dependency :rule => "A"
|
410
|
+
condition_A :q_muscles_joints_bones, "==", :a_7
|
411
|
+
a "Explain", :string
|
412
|
+
end
|
413
|
+
end
|
414
|
+
end
|
415
|
+
"""
|
416
|
+
When I go to the surveys page
|
417
|
+
And I start the "Body" survey
|
418
|
+
Then the question "Explain" should be hidden
|
419
|
+
When I check "Other"
|
420
|
+
Then the question "Explain" should be triggered
|
421
|
+
When I uncheck "Other"
|
422
|
+
Then the question "Explain" should be hidden
|
@@ -473,3 +473,32 @@ Feature: Survey parser
|
|
473
473
|
| Did you take out the trash | true |
|
474
474
|
| Did you do the laundry | true |
|
475
475
|
| Optional comments | false |
|
476
|
+
|
477
|
+
@javascript
|
478
|
+
Scenario: Parsing dependencies with "question_" and "answer_" syntax
|
479
|
+
Given I parse
|
480
|
+
"""
|
481
|
+
survey "Days" do
|
482
|
+
section "Fridays" do
|
483
|
+
q_is_it_friday "Is it Friday?", :pick => :one
|
484
|
+
a_yes "Yes"
|
485
|
+
a_no "No"
|
486
|
+
|
487
|
+
label "woot!"
|
488
|
+
dependency :rule => "A"
|
489
|
+
condition_A :question_is_it_friday, "==", :answer_yes
|
490
|
+
end
|
491
|
+
end
|
492
|
+
"""
|
493
|
+
Then there should be 1 dependency with:
|
494
|
+
| rule |
|
495
|
+
| A |
|
496
|
+
And there should be 1 resolved dependency_condition with:
|
497
|
+
| rule_key |
|
498
|
+
| A |
|
499
|
+
When I go to the surveys page
|
500
|
+
And I start the "Days" survey
|
501
|
+
Then the question "woot!" should be hidden
|
502
|
+
And I choose "Yes"
|
503
|
+
Then the question "woot!" should be triggered
|
504
|
+
|
data/lib/surveyor/common.rb
CHANGED
@@ -37,6 +37,23 @@ module Surveyor
|
|
37
37
|
def generate_api_id
|
38
38
|
UUIDTools::UUID.random_create.to_s
|
39
39
|
end
|
40
|
+
|
41
|
+
##
|
42
|
+
# @private Intended for internal use only.
|
43
|
+
#
|
44
|
+
# Loads and uses either `FasterCSV` (for Ruby 1.8) or the stdlib `CSV`
|
45
|
+
# (for Ruby 1.9+).
|
46
|
+
#
|
47
|
+
# @return [Class] either `CSV` for `FasterCSV`.
|
48
|
+
def csv_impl
|
49
|
+
@csv_impl ||= if RUBY_VERSION < '1.9'
|
50
|
+
require 'fastercsv'
|
51
|
+
FasterCSV
|
52
|
+
else
|
53
|
+
require 'csv'
|
54
|
+
CSV
|
55
|
+
end
|
56
|
+
end
|
40
57
|
end
|
41
58
|
end
|
42
59
|
end
|
@@ -41,11 +41,17 @@ module Surveyor
|
|
41
41
|
|
42
42
|
# Questions
|
43
43
|
def q_text(obj, context=nil)
|
44
|
-
|
44
|
+
|
45
45
|
return image_tag(obj.text) if obj.is_a?(Question) and obj.display_type == "image"
|
46
46
|
return obj.render_question_text(context) if obj.is_a?(Question) and (obj.dependent? or obj.display_type == "label" or obj.part_of_group?)
|
47
|
-
"#{
|
47
|
+
"#{next_question_number(obj)}#{obj.render_question_text(context)}"
|
48
|
+
end
|
49
|
+
|
50
|
+
def next_question_number(question)
|
51
|
+
@n ||= 0
|
52
|
+
"<span class='qnum'>#{@n += 1}) </span>"
|
48
53
|
end
|
54
|
+
|
49
55
|
# def split_text(text = "") # Split text into with "|" delimiter - parts to go before/after input element
|
50
56
|
# {:prefix => text.split("|")[0].blank? ? " " : text.split("|")[0], :postfix => text.split("|")[1] || " "}
|
51
57
|
# end
|
@@ -1,5 +1,3 @@
|
|
1
|
-
require 'fastercsv'
|
2
|
-
require 'csv'
|
3
1
|
require 'rabl'
|
4
2
|
|
5
3
|
module Surveyor
|
@@ -54,8 +52,7 @@ module Surveyor
|
|
54
52
|
qcols = Question.content_columns.map(&:name) - %w(created_at updated_at)
|
55
53
|
acols = Answer.content_columns.map(&:name) - %w(created_at updated_at)
|
56
54
|
rcols = Response.content_columns.map(&:name)
|
57
|
-
|
58
|
-
result = csvlib.generate do |csv|
|
55
|
+
result = Surveyor::Common.csv_impl.generate do |csv|
|
59
56
|
if print_header
|
60
57
|
csv << (access_code ? ["response set access code"] : []) +
|
61
58
|
qcols.map{|qcol| "question.#{qcol}"} +
|
@@ -184,6 +181,7 @@ module Surveyor
|
|
184
181
|
protected
|
185
182
|
|
186
183
|
def dependencies(question_ids = nil)
|
184
|
+
question_ids = survey.sections.map(&:questions).flatten.map(&:id) if responses.blank? and question_ids.blank?
|
187
185
|
deps = Dependency.all(:include => :dependency_conditions,
|
188
186
|
:conditions => {:dependency_conditions => {:question_id => question_ids || responses.map(&:question_id)}})
|
189
187
|
# this is a work around for a bug in active_record in rails 2.3 which incorrectly eager-loads associatins when a
|
@@ -25,6 +25,10 @@ module Surveyor
|
|
25
25
|
# Whitelisting attributes
|
26
26
|
base.send :attr_accessible, :title, :description, :reference_identifier, :data_export_identifier, :common_namespace, :common_identifier, :css_url, :custom_class, :display_order
|
27
27
|
|
28
|
+
# Derived attributes
|
29
|
+
base.send :before_save, :generate_access_code
|
30
|
+
base.send :before_save, :increment_version
|
31
|
+
|
28
32
|
# Class methods
|
29
33
|
base.instance_eval do
|
30
34
|
def to_normalized_string(value)
|
@@ -45,16 +49,6 @@ module Surveyor
|
|
45
49
|
self.display_order ||= Survey.count
|
46
50
|
end
|
47
51
|
|
48
|
-
def title=(value)
|
49
|
-
return if value == self.title
|
50
|
-
surveys = Survey.where(:access_code => Survey.to_normalized_string(value)).order("survey_version DESC")
|
51
|
-
self.survey_version = surveys.first.survey_version.to_i + 1 if surveys.any?
|
52
|
-
self.access_code = Survey.to_normalized_string(value)
|
53
|
-
super(value)
|
54
|
-
# self.access_code = Survey.to_normalized_string(value)
|
55
|
-
# super
|
56
|
-
end
|
57
|
-
|
58
52
|
def active?
|
59
53
|
self.active_as_of?(DateTime.now)
|
60
54
|
end
|
@@ -72,7 +66,22 @@ module Surveyor
|
|
72
66
|
def as_json(options = nil)
|
73
67
|
template_paths = ActionController::Base.view_paths.collect(&:to_path)
|
74
68
|
Rabl.render(self, 'surveyor/export.json', :view_path => template_paths, :format => "hash")
|
75
|
-
end
|
69
|
+
end
|
70
|
+
|
71
|
+
def default_access_code
|
72
|
+
self.class.to_normalized_string(title)
|
73
|
+
end
|
74
|
+
|
75
|
+
def generate_access_code
|
76
|
+
self.access_code ||= default_access_code
|
77
|
+
end
|
78
|
+
|
79
|
+
def increment_version
|
80
|
+
surveys = self.class.select(:survey_version).where(:access_code => access_code).order("survey_version DESC")
|
81
|
+
next_version = surveys.any? ? surveys.first.survey_version.to_i + 1 : 0
|
82
|
+
|
83
|
+
self.survey_version = next_version
|
84
|
+
end
|
76
85
|
end
|
77
86
|
end
|
78
87
|
end
|