sanitized_attributes 1.1.0 → 1.1.1

Sign up to get free protection for your applications and to get access to all the features.
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ README.rdoc
2
+ lib/**/*.rb
3
+ bin/*
4
+ features/**/*.feature
5
+ LICENSE
data/Rakefile ADDED
@@ -0,0 +1,46 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+
4
+ begin
5
+ require 'jeweler'
6
+ Jeweler::Tasks.new do |gem|
7
+ gem.name = "sanitized_attributes"
8
+ gem.summary = %Q{HTML-sanitizing attribute accessors for Ruby and Rails}
9
+ gem.description = %Q{A wrapper to make automatic sanitization of incoming data easier. Uses the sanitize gem and works in both plain Ruby and Rails projects.}
10
+ gem.email = "matthew.boeh@gmail.com"
11
+ gem.homepage = "http://github.com/mboeh/sanitized_attributes"
12
+ gem.authors = ["Matthew Boeh", "CrowdCompass, Inc."]
13
+ gem.add_development_dependency "rspec", ">= 1.2.9"
14
+ gem.add_dependency "sanitize", "> 0"
15
+ end
16
+ Jeweler::GemcutterTasks.new
17
+ rescue LoadError
18
+ puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
19
+ end
20
+
21
+ require 'spec/rake/spectask'
22
+ Spec::Rake::SpecTask.new(:spec) do |spec|
23
+ spec.libs << 'lib' << 'spec'
24
+ spec.spec_files = FileList['spec/**/*_spec.rb']
25
+ end
26
+
27
+ Spec::Rake::SpecTask.new(:rcov) do |spec|
28
+ spec.libs << 'lib' << 'spec'
29
+ spec.pattern = 'spec/**/*_spec.rb'
30
+ spec.rcov = true
31
+ spec.rcov_opts = ['--exclude', File.expand_path("~/.rvm"), "--exclude", "spec"]
32
+ end
33
+
34
+ task :spec => :check_dependencies
35
+
36
+ task :default => :spec
37
+
38
+ require 'rake/rdoctask'
39
+ Rake::RDocTask.new do |rdoc|
40
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
41
+
42
+ rdoc.rdoc_dir = 'rdoc'
43
+ rdoc.title = "sanitized_attributes #{version}"
44
+ rdoc.rdoc_files.include('README*')
45
+ rdoc.rdoc_files.include('lib/**/*.rb')
46
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 1.1.1
@@ -0,0 +1,90 @@
1
+ require 'rubygems'
2
+ require 'sanitize'
3
+ require 'sanitized_attributes/sanitized_attribute'
4
+
5
+ module SanitizedAttributes
6
+
7
+ def self.included(into)
8
+ into.extend(ClassMethods)
9
+ end
10
+
11
+ class << self
12
+
13
+ def add_option(name, &blk)
14
+ @option_transforms = nil
15
+ @options ||= {}
16
+ @options[name] = blk
17
+ end
18
+
19
+ def add_profile(name, options = {})
20
+ @profiles ||= {}
21
+ @profiles[name] = options
22
+ end
23
+
24
+ def profile(name)
25
+ @profiles ||= {}
26
+ @profiles[name] || {}
27
+ end
28
+
29
+ def sanitize_options(options)
30
+ pr =
31
+ if options.kind_of?(Symbol)
32
+ profile(options)
33
+ else
34
+ options
35
+ end
36
+ o = merge_options(default_profile, pr)
37
+ o
38
+ end
39
+
40
+ protected
41
+
42
+ def default_profile
43
+ merge_options(profile(:default), obligatory_options)
44
+ end
45
+
46
+ def merge_options(ops, new_ops)
47
+ final_ops = ops.dup
48
+ new_ops.each do |key,val|
49
+ old = final_ops[key]
50
+ if key == :transformers
51
+ final_ops[key] ||= []
52
+ final_ops[key] = ([old] + [val]).flatten.uniq.compact
53
+ else
54
+ final_ops[key] = val
55
+ end
56
+ final_ops.delete(key) if final_ops[key].nil?
57
+ end
58
+ return final_ops
59
+ end
60
+
61
+ def obligatory_options
62
+ { :transformers => option_transforms }
63
+ end
64
+
65
+ def option_transforms
66
+ @option_transforms ||=
67
+ begin
68
+ if @options
69
+ @options.map do |name, tproc|
70
+ lambda do |env|
71
+ tproc.call(env, env[:config][name]) if env[:config][name]
72
+ end
73
+ end
74
+ else
75
+ []
76
+ end
77
+ end
78
+ end
79
+ end
80
+
81
+
82
+ module ClassMethods
83
+
84
+ def sanitize_attribute(attr_name, options = {})
85
+ SanitizedAttribute.add(self, attr_name, options)
86
+ end
87
+
88
+ end
89
+
90
+ end
@@ -0,0 +1,48 @@
1
+ module SanitizedAttributes; class SanitizedAttribute
2
+
3
+ def initialize(attr_name, options = {})
4
+ @attr_name = attr_name
5
+ @options = options
6
+ end
7
+
8
+ def sanitize(content)
9
+ Sanitize.clean("<SPURIOUS-TOPLEVEL>" + content + "</SPURIOUS-TOPLEVEL>", sanitize_config).gsub(%r{</?SPURIOUS-TOPLEVEL>}, "")
10
+ end
11
+
12
+ def define_ar_writer_method(klass)
13
+ this = self
14
+ attr_name = @attr_name
15
+ klass.send(:define_method, "#{@attr_name}=") {|value|
16
+ send(:write_attribute, attr_name, this.sanitize(value))
17
+ }
18
+ end
19
+
20
+ def define_writer_method(klass)
21
+ this = self
22
+ attr_name = @attr_name
23
+ klass.send(:define_method, "#{@attr_name}_with_sanitization=") {|value|
24
+ send("#{attr_name}_without_sanitization=", this.sanitize(value))
25
+ }
26
+ end
27
+
28
+ protected
29
+
30
+ def sanitize_config
31
+ SanitizedAttributes.sanitize_options(@options)
32
+ end
33
+
34
+ class << self
35
+
36
+ def add(klass, attr_name, options = {})
37
+ attrib = new(attr_name, options)
38
+ if klass.respond_to?(:alias_method_chain)
39
+ attrib.define_ar_writer_method(klass)
40
+ else
41
+ attrib.define_writer_method(klass)
42
+ klass.send(:alias_method, "#{attr_name}_without_sanitization=", "#{attr_name}=")
43
+ klass.send(:alias_method, "#{attr_name}=", "#{attr_name}_with_sanitization=")
44
+ end
45
+ end
46
+
47
+ end
48
+ end; end
@@ -0,0 +1,57 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{sanitized_attributes}
8
+ s.version = "1.1.1"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Matthew Boeh", "CrowdCompass, Inc."]
12
+ s.date = %q{2011-01-27}
13
+ s.description = %q{A wrapper to make automatic sanitization of incoming data easier. Uses the sanitize gem and works in both plain Ruby and Rails projects.}
14
+ s.email = %q{matthew.boeh@gmail.com}
15
+ s.extra_rdoc_files = [
16
+ "LICENSE",
17
+ "README.rdoc"
18
+ ]
19
+ s.files = [
20
+ ".document",
21
+ "LICENSE",
22
+ "README.rdoc",
23
+ "Rakefile",
24
+ "VERSION",
25
+ "lib/sanitized_attributes.rb",
26
+ "lib/sanitized_attributes/sanitized_attribute.rb",
27
+ "sanitized_attributes.gemspec",
28
+ "spec/sanitized_attributes_spec.rb",
29
+ "spec/spec.opts",
30
+ "spec/spec_helper.rb"
31
+ ]
32
+ s.homepage = %q{http://github.com/mboeh/sanitized_attributes}
33
+ s.require_paths = ["lib"]
34
+ s.rubygems_version = %q{1.3.7}
35
+ s.summary = %q{HTML-sanitizing attribute accessors for Ruby and Rails}
36
+ s.test_files = [
37
+ "spec/sanitized_attributes_spec.rb",
38
+ "spec/spec_helper.rb"
39
+ ]
40
+
41
+ if s.respond_to? :specification_version then
42
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
43
+ s.specification_version = 3
44
+
45
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
46
+ s.add_development_dependency(%q<rspec>, [">= 1.2.9"])
47
+ s.add_runtime_dependency(%q<sanitize>, ["> 0"])
48
+ else
49
+ s.add_dependency(%q<rspec>, [">= 1.2.9"])
50
+ s.add_dependency(%q<sanitize>, ["> 0"])
51
+ end
52
+ else
53
+ s.add_dependency(%q<rspec>, [">= 1.2.9"])
54
+ s.add_dependency(%q<sanitize>, ["> 0"])
55
+ end
56
+ end
57
+
@@ -0,0 +1,67 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "SanitizedAttributes" do
4
+
5
+ before do
6
+ @klass = Class.new do
7
+ include SanitizedAttributes
8
+ attr_accessor :orz
9
+ attr_accessor :vux
10
+ end
11
+ SanitizedAttributes.add_option(:no_empties) do |env, forbidden_empties|
12
+ if env[:node].content.empty?
13
+ if forbidden_empties.include?(env[:node_name])
14
+ {:node => Nokogiri::XML::Text.new("", env[:node].document)}
15
+ end
16
+ end
17
+ end
18
+ SanitizedAttributes.add_option(:gsub) do |env, substitutions|
19
+ env[:node].children.each do |node|
20
+ if node.kind_of?(Nokogiri::XML::Text)
21
+ text = node.content
22
+ substitutions.each do |regex, subst|
23
+ text.gsub!(regex, subst)
24
+ end
25
+ node.content = text
26
+ end
27
+ end
28
+ nil
29
+ end
30
+ SanitizedAttributes.add_profile(:default, :gsub => { "\r" => "" })
31
+ SanitizedAttributes.add_profile(:quotes_only, :elements => %w[blockquote])
32
+ end
33
+
34
+ it "removes all HTML by default" do
35
+ @klass.module_eval do
36
+ sanitize_attribute :orz
37
+ end
38
+ obj = @klass.new
39
+ obj.orz = "<a>Orz are not *many bubbles* like <p/>*campers*. <p></p>Orz <b>are just</b> Orz. <p>- Orz</p>"
40
+ obj.orz.should == "Orz are not *many bubbles* like *campers*. Orz are just Orz. - Orz"
41
+ end
42
+
43
+ it "allows a default sanitizing profile to be set up" do
44
+ SanitizedAttributes.add_profile(:default, Sanitize::Config::BASIC)
45
+ @klass.module_eval do
46
+ sanitize_attribute :orz
47
+ end
48
+ obj = @klass.new
49
+ obj.orz = "<a>Orz are not *many bubbles* like <p/>*campers*. <p></p>Orz <b>are just</b> Orz. <p>- Orz</p>"
50
+ obj.orz.should == "<a rel=\"nofollow\">Orz are not *many bubbles* like <p></p>*campers*. <p></p>Orz <b>are just</b> Orz. <p>- Orz</p></a>"
51
+ SanitizedAttributes.add_profile(:default, Sanitize::Config::BASIC.merge(:no_empties => %w[p]))
52
+ obj.orz = "<a>Orz are not *many bubbles* like <p/>*campers*. <p></p>Orz <b>are just</b> Orz. <p>- Orz</p>"
53
+ obj.orz.should == "<a rel=\"nofollow\">Orz are not *many bubbles* like *campers*. Orz <b>are just</b> Orz. <p>- Orz</p></a>"
54
+ end
55
+
56
+ it "sanitizes attributes with custom options and profiles" do
57
+ @klass.module_eval do
58
+ sanitize_attribute :orz, :elements => %w[p], :no_empties => %w[p]
59
+ sanitize_attribute :vux, :quotes_only
60
+ end
61
+ obj = @klass.new
62
+ obj.vux = "<blockquote>Our special today is <b>particle fragmentation!</b></blockquote> - VUX"
63
+ obj.vux.should == "<blockquote>Our special today is particle fragmentation!</blockquote> - VUX"
64
+ obj.orz = "\r\nOrz are not *many bubbles* like <p/>*campers*. <p></p>Orz <b>\r\nare just</b> Orz. <p>- Orz</p>"
65
+ obj.orz.should == "\nOrz are not *many bubbles* like *campers*. Orz \nare just Orz. <p>- Orz</p>"
66
+ end
67
+ end
data/spec/spec.opts ADDED
@@ -0,0 +1 @@
1
+ --color
@@ -0,0 +1,9 @@
1
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
2
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
3
+ require 'sanitized_attributes'
4
+ require 'spec'
5
+ require 'spec/autorun'
6
+
7
+ Spec::Runner.configure do |config|
8
+
9
+ end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sanitized_attributes
3
3
  version: !ruby/object:Gem::Version
4
- hash: 19
4
+ hash: 17
5
5
  prerelease: false
6
6
  segments:
7
7
  - 1
8
8
  - 1
9
- - 0
10
- version: 1.1.0
9
+ - 1
10
+ version: 1.1.1
11
11
  platform: ruby
12
12
  authors:
13
13
  - Matthew Boeh
@@ -59,8 +59,17 @@ extra_rdoc_files:
59
59
  - LICENSE
60
60
  - README.rdoc
61
61
  files:
62
+ - .document
62
63
  - LICENSE
63
64
  - README.rdoc
65
+ - Rakefile
66
+ - VERSION
67
+ - lib/sanitized_attributes.rb
68
+ - lib/sanitized_attributes/sanitized_attribute.rb
69
+ - sanitized_attributes.gemspec
70
+ - spec/sanitized_attributes_spec.rb
71
+ - spec/spec.opts
72
+ - spec/spec_helper.rb
64
73
  has_rdoc: true
65
74
  homepage: http://github.com/mboeh/sanitized_attributes
66
75
  licenses: []
@@ -95,5 +104,6 @@ rubygems_version: 1.3.7
95
104
  signing_key:
96
105
  specification_version: 3
97
106
  summary: HTML-sanitizing attribute accessors for Ruby and Rails
98
- test_files: []
99
-
107
+ test_files:
108
+ - spec/sanitized_attributes_spec.rb
109
+ - spec/spec_helper.rb