webfeed 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. data/MIT-LICENSE +20 -0
  2. data/README.rdoc +49 -0
  3. data/Rakefile +27 -0
  4. data/lib/feed_reader.rb +36 -0
  5. data/lib/generators/web_feed/add_image_generator.rb +15 -0
  6. data/lib/generators/web_feed/install_generator.rb +89 -0
  7. data/lib/generators/web_feed/keyword_generator.rb +15 -0
  8. data/lib/generators/web_feed/news_generator.rb +15 -0
  9. data/lib/generators/web_feed/resource_generator.rb +15 -0
  10. data/lib/generators/web_feed/templates/controllers/keywords_controller.rb.erb +34 -0
  11. data/lib/generators/web_feed/templates/controllers/news_controller.rb.erb +24 -0
  12. data/lib/generators/web_feed/templates/controllers/resources_controller.rb.erb +40 -0
  13. data/lib/generators/web_feed/templates/migrations/add_attachment_image_to_news.rb.erb +15 -0
  14. data/lib/generators/web_feed/templates/migrations/create_keywords.rb.erb +10 -0
  15. data/lib/generators/web_feed/templates/migrations/create_news.rb.erb +14 -0
  16. data/lib/generators/web_feed/templates/migrations/create_resources.rb.erb +12 -0
  17. data/lib/generators/web_feed/templates/models/keyword.rb.erb +17 -0
  18. data/lib/generators/web_feed/templates/models/news.rb.erb +26 -0
  19. data/lib/generators/web_feed/templates/models/resource.rb.erb +27 -0
  20. data/lib/generators/web_feed/templates/stylesheets/webfeed.css +144 -0
  21. data/lib/generators/web_feed/templates/views/keywords/_form.html.erb +28 -0
  22. data/lib/generators/web_feed/templates/views/keywords/edit.html.erb +2 -0
  23. data/lib/generators/web_feed/templates/views/keywords/index.html.erb +14 -0
  24. data/lib/generators/web_feed/templates/views/keywords/new.html.erb +2 -0
  25. data/lib/generators/web_feed/templates/views/layouts/_webfeed.html.erb +5 -0
  26. data/lib/generators/web_feed/templates/views/layouts/webfeed.html.erb +11 -0
  27. data/lib/generators/web_feed/templates/views/news/index.html.erb +16 -0
  28. data/lib/generators/web_feed/templates/views/news/show.html.erb +9 -0
  29. data/lib/generators/web_feed/templates/views/resources/_form.html.erb +34 -0
  30. data/lib/generators/web_feed/templates/views/resources/edit.html.erb +2 -0
  31. data/lib/generators/web_feed/templates/views/resources/index.html.erb +29 -0
  32. data/lib/generators/web_feed/templates/views/resources/new.html.erb +2 -0
  33. data/lib/tasks/webfeed_tasks.rake +4 -0
  34. data/lib/webfeed/version.rb +3 -0
  35. data/lib/webfeed.rb +4 -0
  36. metadata +201 -0
data/MIT-LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright 2012 YOURNAME
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,49 @@
1
+ = Webfeed
2
+
3
+ This project uses MIT-LICENSE.
4
+
5
+
6
+ == Installation
7
+
8
+ In <b>Rails 3</b>, add following line to your Gemfile and run the <tt>bundle</tt> command.
9
+
10
+ gem "web_feed"
11
+
12
+ In <b>Rails 2</b>, add following line to your environment.rb file.
13
+
14
+ config.gem "web_feed"
15
+
16
+ == Getting Started
17
+
18
+ There couple of generators. you can run something like <tt>rails g web_feed:install -h</tt> to see what they do
19
+
20
+ web_feed:install
21
+ web_feed:resource
22
+ web_feed:keyword
23
+ web_feed:news
24
+ web_feed:add_image
25
+
26
+ Running <tt>rails g web_feed:install -mvc</tt> will create all migrations, models, views, controllers and routings and a basic stylesheet file.
27
+
28
+ In case you want to rename the entities you can run this command:
29
+
30
+ rails g web_feed:install -r [RESOURCE_NAME] -n [NEWS_NAME] -k [KEYWORD_NAME] -mvc
31
+ rails g web_feed:install -r resource -n post -k keyword -mvc
32
+
33
+ === Basic View
34
+
35
+ Add following line to your main layout to see the WebFeed pages with basic styling
36
+
37
+ <%= stylesheet_link_tag "webfeed", :media => "all" %>
38
+
39
+ And add this line to see the what pages you have in WebFeed
40
+
41
+ <%= render 'layouts/webfeed' %>
42
+
43
+ === Try It
44
+
45
+ After generating file and migrating <tt>rails db:migrate</tt>. Try to add some RSS resources such as <i>http://feeds.gizmodo.com.au/GizmodoAustralia</i> or <i>http://techcrunch.com/feed/</i> and some keywords such as <i>iphone</i>, <i>samsung</i> and <i>facebook</i>. Then try to update resources from index page.
46
+
47
+ == Testing SPECS
48
+
49
+ bundle exec guard
data/Rakefile ADDED
@@ -0,0 +1,27 @@
1
+ #!/usr/bin/env rake
2
+ begin
3
+ require 'bundler/setup'
4
+ rescue LoadError
5
+ puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
6
+ end
7
+ begin
8
+ require 'rdoc/task'
9
+ rescue LoadError
10
+ require 'rdoc/rdoc'
11
+ require 'rake/rdoctask'
12
+ RDoc::Task = Rake::RDocTask
13
+ end
14
+
15
+ RDoc::Task.new(:rdoc) do |rdoc|
16
+ rdoc.rdoc_dir = 'rdoc'
17
+ rdoc.title = 'Webfeed'
18
+ rdoc.options << '--line-numbers'
19
+ rdoc.rdoc_files.include('README.rdoc')
20
+ rdoc.rdoc_files.include('lib/**/*.rb')
21
+ end
22
+
23
+
24
+
25
+
26
+ Bundler::GemHelper.install_tasks
27
+
@@ -0,0 +1,36 @@
1
+ module FeedReader
2
+
3
+ require 'open-uri'
4
+ require 'nokogiri'
5
+
6
+ class Reader
7
+
8
+ attr_accessor :list
9
+
10
+ def initialize(uri)
11
+ @doc = Nokogiri::XML(open(uri))
12
+ @list = []
13
+ @doc.css('item').each do |item|
14
+ @list << [ item.at_css('title').text, ActionController::Base.helpers.sanitize(item.at_css('description').text,:tags=>[]), Nokogiri::HTML(item.css('description').text).at_css('img').attributes['src'].value, item.at_css('link').text ] # title, description, image, link
15
+ end
16
+ end
17
+
18
+ def filter( inc_words, exc_words=[] )
19
+ template = '\W(?)\W'
20
+ inc = template.gsub '?', inc_words.join('|')
21
+ exc = template.gsub '?', exc_words.join('|')
22
+ list = []
23
+ @list.each do |item|
24
+ str = " #{item[0]} #{item[1]} "
25
+ if inc_words.empty? || !(str =~ Regexp.new(inc,'i')).nil?
26
+ if exc_words.empty? || (str =~ Regexp.new(inc,'i')).nil?
27
+ list<<item
28
+ end
29
+ end
30
+ end
31
+ list
32
+ end
33
+
34
+ end
35
+
36
+ end
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record'
2
+
3
+ module WebFeed
4
+
5
+ class AddImageGenerator < ActiveRecord::Generators::Base
6
+
7
+ source_root File.expand_path('../templates', __FILE__)
8
+
9
+ def generate_migration
10
+ migration_template "migrations/add_attachment_image_to_news.rb.erb", "db/migrate/add_attachment_image_to_#{name.downcase.underscore.pluralize}.rb"
11
+ end
12
+
13
+ end
14
+
15
+ end
@@ -0,0 +1,89 @@
1
+ require 'rails/generators'
2
+
3
+ module WebFeed
4
+
5
+ class InstallGenerator < Rails::Generators::Base
6
+
7
+ class_option :resource , :type => :string, :desc => 'Change the name for resources' , :default => 'resource' , :aliases => '-r'
8
+ class_option :keyword , :type => :string, :desc => 'Change the name for keywords' , :default => 'keyword' , :aliases => '-k'
9
+ class_option :news , :type => :string, :desc => 'Change the name for news' , :default => 'news' , :aliases => '-n'
10
+
11
+ class_option :include_models , :type => :boolean, :desc => 'Create model files' , :aliases => '-m'
12
+ class_option :include_controllers , :type => :boolean, :desc => 'Create controller files' , :aliases => '-c'
13
+ class_option :include_views , :type => :boolean, :desc => 'Create view files' , :aliases => '-v'
14
+
15
+ desc "Create routes, migrations, models, controllers, views"
16
+
17
+ source_root File.expand_path('../templates', __FILE__)
18
+
19
+ def init
20
+ route <<-RES
21
+ resources :#{resource.pluralize} do
22
+ member do
23
+ post :read
24
+ end
25
+ end
26
+ RES
27
+ route <<-NEWS
28
+ resources :#{news.pluralize} do
29
+ member do
30
+ get "/:title(.:format)", :action => :show, :as => 'read'
31
+ post :publish
32
+ post :unpublish
33
+ end
34
+ end
35
+ NEWS
36
+ route "resources :#{keyword.pluralize}"
37
+ end
38
+
39
+ def generate_migration
40
+ generate "web_feed:resource #{resource}"
41
+ generate "web_feed:news #{news}"
42
+ generate "web_feed:keyword #{keyword}"
43
+ generate "web_feed:add_image #{news}"
44
+ end
45
+
46
+ def generate_app
47
+ if options.include_models?
48
+ template "models/resource.rb.erb", "#{Rails.root}/app/models/#{resource}.rb"
49
+ template "models/news.rb.erb", "#{Rails.root}/app/models/#{news}.rb"
50
+ template "models/keyword.rb.erb", "#{Rails.root}/app/models/#{keyword}.rb"
51
+ end
52
+ if options.include_controllers?
53
+ template "controllers/resources_controller.rb.erb", "#{Rails.root}/app/controllers/#{resource.pluralize}_controller.rb"
54
+ template "controllers/news_controller.rb.erb", "#{Rails.root}/app/controllers/#{news.pluralize}_controller.rb"
55
+ template "controllers/keywords_controller.rb.erb", "#{Rails.root}/app/controllers/#{keyword.pluralize}_controller.rb"
56
+ end
57
+ if options.include_views?
58
+ %w( index new edit _form).each do |file|
59
+ template "views/resources/#{file}.html.erb", "#{Rails.root}/app/views/#{resource.pluralize}/#{file}.html.erb"
60
+ end
61
+ %w( index new edit _form).each do |file|
62
+ template "views/keywords/#{file}.html.erb", "#{Rails.root}/app/views/#{keyword.pluralize}/#{file}.html.erb"
63
+ end
64
+ %w( index show).each do |file|
65
+ template "views/news/#{file}.html.erb", "#{Rails.root}/app/views/#{news.pluralize}/#{file}.html.erb"
66
+ end
67
+ copy_file "views/layouts/webfeed.html.erb", "#{Rails.root}/app/views/layouts/webfeed.html.erb"
68
+ template "views/layouts/_webfeed.html.erb", "#{Rails.root}/app/views/layouts/_webfeed.html.erb"
69
+ copy_file "stylesheets/webfeed.css", "#{Rails.root}/app/assets/stylesheets/webfeed.css"
70
+ end
71
+ end
72
+
73
+ protected
74
+
75
+ def resource
76
+ options.resource.downcase.singularize
77
+ end
78
+
79
+ def keyword
80
+ options.keyword.downcase.singularize
81
+ end
82
+
83
+ def news
84
+ options.news.downcase.singularize
85
+ end
86
+
87
+ end
88
+
89
+ end
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record'
2
+
3
+ module WebFeed
4
+
5
+ class KeywordGenerator < ActiveRecord::Generators::Base
6
+
7
+ source_root File.expand_path('../templates', __FILE__)
8
+
9
+ def generate_migration
10
+ migration_template "migrations/create_keywords.rb.erb", "db/migrate/create_#{name.downcase.underscore.pluralize}.rb"
11
+ end
12
+
13
+ end
14
+
15
+ end
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record'
2
+
3
+ module WebFeed
4
+
5
+ class NewsGenerator < ActiveRecord::Generators::Base
6
+
7
+ source_root File.expand_path('../templates', __FILE__)
8
+
9
+ def generate_migration
10
+ migration_template "migrations/create_news.rb.erb", "db/migrate/create_#{name.downcase.underscore.pluralize}.rb"
11
+ end
12
+
13
+ end
14
+
15
+ end
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record'
2
+
3
+ module WebFeed
4
+
5
+ class ResourceGenerator < ActiveRecord::Generators::Base
6
+
7
+ source_root File.expand_path('../templates', __FILE__)
8
+
9
+ def generate_migration
10
+ migration_template "migrations/create_resources.rb.erb", "db/migrate/create_#{name.downcase.underscore.pluralize}.rb"
11
+ end
12
+
13
+ end
14
+
15
+ end
@@ -0,0 +1,34 @@
1
+ class <%= keyword.pluralize.camelcase %>Controller < ApplicationController
2
+
3
+ def index
4
+ @positive = <%= keyword.camelcase %>.includables
5
+ @negative = <%= keyword.camelcase %>.excludables
6
+ end
7
+
8
+ def new
9
+ @keyword = <%= keyword.camelcase %>.new
10
+ end
11
+
12
+ def create
13
+ @keyword = <%= keyword.camelcase %>.new params[:<%=keyword%>]
14
+ if @keyword.save
15
+ redirect_to root_path
16
+ else
17
+ render :new
18
+ end
19
+ end
20
+
21
+ def edit
22
+ @keyword = <%= keyword.camelcase %>.find params[:id]
23
+ end
24
+
25
+ def update
26
+ @keyword = Keyword.find params[:id]
27
+ if @keyword.update_attributes(params[:<%=keyword%>])
28
+ redirect_to root_path
29
+ else
30
+ render :edit
31
+ end
32
+ end
33
+
34
+ end
@@ -0,0 +1,24 @@
1
+ class <%= news.pluralize.camelcase %>Controller < ApplicationController
2
+
3
+ def index
4
+ @news = <%= news.camelcase %>.all
5
+ end
6
+
7
+ def show
8
+ @news = <%= news.camelcase %>.find params[:id]
9
+ render :layout => 'webfeed'
10
+ end
11
+
12
+ def publish
13
+ @news = <%= news.camelcase %>.find params[:id]
14
+ @news.update_attributes( :is_published => true )
15
+ redirect_to root_path
16
+ end
17
+
18
+ def unpublish
19
+ @news = <%= news.camelcase %>.find params[:id]
20
+ @news.update_attributes( :is_published => false )
21
+ redirect_to root_path
22
+ end
23
+
24
+ end
@@ -0,0 +1,40 @@
1
+ class <%= resource.pluralize.camelcase %>Controller < ApplicationController
2
+
3
+ def index
4
+ @expired = <%= resource.camelcase %>.expired
5
+ @uptodated = <%= resource.camelcase %>.uptodated
6
+ end
7
+
8
+ def read
9
+ @resource = <%= resource.camelcase %>.find params[:id]
10
+ @resource.read_and_update
11
+ redirect_to <%=resource.pluralize%>_path
12
+ end
13
+
14
+ def new
15
+ @resource = <%= resource.camelcase %>.new
16
+ end
17
+
18
+ def create
19
+ @resource = <%= resource.camelcase %>.new params[:<%=resource%>]
20
+ if @resource.save
21
+ redirect_to <%=resource.pluralize%>_path
22
+ else
23
+ render :new
24
+ end
25
+ end
26
+
27
+ def edit
28
+ @resource = <%= resource.camelcase %>.find params[:id]
29
+ end
30
+
31
+ def update
32
+ @resource = <%= resource.camelcase %>.find params[:id]
33
+ if @resource.update_attributes(params[:<%=resource%>])
34
+ redirect_to <%=resource.pluralize%>_path
35
+ else
36
+ render :edit
37
+ end
38
+ end
39
+
40
+ end
@@ -0,0 +1,15 @@
1
+ class <%= migration_class_name %> < ActiveRecord::Migration
2
+ def self.up
3
+ add_column :<%= table_name %>, :image_file_name, :string
4
+ add_column :<%= table_name %>, :image_content_type, :string
5
+ add_column :<%= table_name %>, :image_file_size, :integer
6
+ add_column :<%= table_name %>, :image_updated_at, :datetime
7
+ end
8
+
9
+ def self.down
10
+ remove_column :<%= table_name %>, :image_file_name
11
+ remove_column :<%= table_name %>, :image_content_type
12
+ remove_column :<%= table_name %>, :image_file_size
13
+ remove_column :<%= table_name %>, :image_updated_at
14
+ end
15
+ end
@@ -0,0 +1,10 @@
1
+ class <%= migration_class_name %> < ActiveRecord::Migration
2
+ def change
3
+ create_table :<%= table_name %> do |t|
4
+ t.string :phrase
5
+ t.boolean :is_negative
6
+
7
+ t.timestamps
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,14 @@
1
+ class <%= migration_class_name %> < ActiveRecord::Migration
2
+ def change
3
+ create_table :<%= table_name %> do |t|
4
+ t.string :title
5
+ t.text :description
6
+ t.string :url
7
+ t.string :image_url
8
+ t.boolean :is_published, :default => false
9
+ t.string :uuid, :null => false
10
+
11
+ t.timestamps
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,12 @@
1
+ class <%= migration_class_name %> < ActiveRecord::Migration
2
+ def change
3
+ create_table :<%= table_name %> do |t|
4
+ t.string :url
5
+ t.string :name
6
+ t.integer :frequency
7
+ t.timestamp :checked_at
8
+
9
+ t.timestamps
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,17 @@
1
+ class <%= keyword.camelcase %> < ActiveRecord::Base
2
+ attr_accessible :is_negative, :phrase
3
+
4
+ validates_presence_of :phrase
5
+
6
+ scope :excludables, where( 'is_negative IS TRUE' )
7
+ scope :includables, where( 'is_negative IS NOT TRUE' )
8
+
9
+ def self.includables_list
10
+ <%= keyword.camelcase %>.includables.collect{ |i| i=i.phrase }
11
+ end
12
+
13
+ def self.excludables_list
14
+ <%= keyword.camelcase %>.excludables.collect{ |i| i=i.phrase }
15
+ end
16
+
17
+ end
@@ -0,0 +1,26 @@
1
+ class <%= news.camelcase %> < ActiveRecord::Base
2
+
3
+ require 'digest/md5'
4
+ require "open-uri"
5
+
6
+ attr_accessible :description, :image, :image_url, :title, :url, :is_published
7
+ has_attached_file :image, :styles => { :thumb => "100x80>", :url => "/system/:class/:id/:style/:filename" }
8
+
9
+ validates_presence_of :title, :url
10
+ validates_uniqueness_of :uuid, :on => :create
11
+
12
+ default_scope :order => 'created_at DESC'
13
+
14
+ scope :published, where("is_published IS TRUE")
15
+
16
+ def url=(url)
17
+ write_attribute :url, url
18
+ self.uuid = Digest::MD5.hexdigest(url)
19
+ end
20
+
21
+ def image_url=(url)
22
+ write_attribute :image_url, url
23
+ self.image = open(url)
24
+ end
25
+
26
+ end
@@ -0,0 +1,27 @@
1
+ class <%= resource.camelcase %> < ActiveRecord::Base
2
+
3
+ attr_accessible :frequency, :name, :url, :checked_at
4
+
5
+ validates_presence_of :url, :frequency
6
+
7
+ scope :expired, where("checked_at IS NULL OR TIMESTAMPDIFF(MINUTE, checked_at, '#{DateTime.now.utc}') > frequency")
8
+ scope :uptodated, where("TIMESTAMPDIFF(MINUTE, checked_at, '#{DateTime.now.utc}') <= frequency")
9
+
10
+ def read
11
+ if self.checked_at.nil? || (DateTime.now.to_i - DateTime.parse(self.checked_at.utc.to_s).to_i)/60 > self.frequency
12
+ reader = FeedReader::Reader.new self.url
13
+ news = reader.filter <%= keyword.camelcase %>.includables_list
14
+ end
15
+ news
16
+ end
17
+
18
+ def read_and_update
19
+ items = read
20
+ items.each do |item|
21
+ <%= news.camelcase %>.create :title => item[0], :description => item[1], :image_url => item[2], :url => item[3]
22
+ end
23
+ update_attributes( :checked_at => DateTime.now )
24
+ items
25
+ end
26
+
27
+ end
@@ -0,0 +1,144 @@
1
+ /*
2
+ * This is a manifest file that'll be compiled into application.css, which will include all the files
3
+ * listed below.
4
+ *
5
+ * Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
6
+ * or vendor/assets/stylesheets of plugins, if any, can be referenced here using a relative path.
7
+ *
8
+ * You're free to add application-wide styles to this file and they'll appear at the top of the
9
+ * compiled file, but it's generally better to create a new file per style scope.
10
+ *
11
+ *= require_self
12
+ *= require_tree .
13
+ */
14
+ body{
15
+ font-family: arial, tahoma;
16
+ font-size: 12px;
17
+ color: #111;
18
+ }
19
+ .menu{
20
+ background: #222;
21
+ font-size: 14px;
22
+ padding: 10px;
23
+ }
24
+ .menu a{
25
+ padding: 5px;
26
+ margin: 0px 10px;
27
+ color: #fff;
28
+ font-weight: bold;
29
+ text-decoration: none;
30
+ }
31
+ .menu a:hover{
32
+ background: #000;
33
+ }
34
+ h1,h2,h3,h4,h5{
35
+ font-size: 12px;
36
+ font-weight: bold;
37
+ color: #1975D1;
38
+ margin: 0px;
39
+ padding: 6px 0px 2px;
40
+ }
41
+ a{
42
+ color: #1975D1;
43
+ }
44
+ h1,
45
+ h1 a{
46
+ font-size: 22px;
47
+ color: #2D519B;
48
+ }
49
+ h1 a,h2 a,h3 a,h4 a,h5 a{ text-decoration: none; }
50
+ h1 a:hover,h2 a:hover,h3 a:hover,h4 a:hover,h5 a:hover{ text-decoration: underline; }
51
+ h2{
52
+ font-size: 18px;
53
+ color: #D69808;
54
+ }
55
+ h3{
56
+ font-size: 16px;
57
+ color: #D6083B;
58
+ }
59
+ h4{
60
+ font-size: 14px;
61
+ color: #222;
62
+ }
63
+ h4, h5{
64
+ padding: 2px 0px 0px;
65
+ }
66
+ .inline{
67
+ display: inline-block;
68
+ *display: inline;
69
+ *zoom: 1;
70
+ }
71
+ .resource,
72
+ .news,
73
+ .keyword{
74
+ border: #111 1px dashed;
75
+ background: #eee;
76
+ padding: 5px;
77
+ margin: 2px;
78
+ }
79
+ .news.published{
80
+ background: #EAD144;
81
+ }
82
+ .resource:hover,
83
+ .news:hover,
84
+ .keyword:hover{
85
+ background: #aaa;
86
+ }
87
+ .resource .frequency{
88
+ font-size: 12px;
89
+ font-weight: bold;
90
+ color: #1975D1;
91
+ }
92
+ .resource form{ display: inline; }
93
+ .resource a,
94
+ .keyword a{
95
+ color: #444;
96
+ padding: 0px 5px;
97
+ }
98
+ .errors{
99
+ background: #B22323;
100
+ border: #6D0303 1px solid;
101
+ color: #fff;
102
+ padding: 10px;
103
+ font-weight: bold;
104
+ }
105
+ .errors h2{
106
+ color: #fff;
107
+ }
108
+ .daily_header{
109
+ height: 140px;
110
+ border-bottom: #eee 3px solid;
111
+ background: #222;
112
+ color: #fff;
113
+ padding: 0px 10px;
114
+ }
115
+ .daily_header h2{
116
+ padding: 0px 0px 10px;
117
+ }
118
+ .daily_reader{
119
+ position: absolute;
120
+ top: 143px;
121
+ bottom: 0px;
122
+ width: 100%;
123
+ }
124
+ .daily_reader iframe{
125
+ width: 100%;
126
+ height: 100%;
127
+ }
128
+ body.daily{
129
+ overflow: hidden;
130
+ margin: 0px;
131
+ padding: 0px;
132
+ }
133
+ .desc{
134
+ width: 800px;
135
+ vertical-align: top;
136
+ margin: 0px;
137
+ padding: 0px 10px;
138
+ }
139
+ .daily_header h1 span{
140
+ color: #E5D600;
141
+ }
142
+ .daily_header .desc{
143
+ width: 500px;
144
+ }
@@ -0,0 +1,28 @@
1
+ <%%= form_for @keyword do |f| %>
2
+ <%% if @keyword.errors.any? %>
3
+ <div class="errors">
4
+ <h2><%%= pluralize(@keyword.errors.count, "error") %> prohibited this keyword from being saved:</h2>
5
+
6
+ <ul>
7
+ <%% @keyword.errors.full_messages.each do |msg| %>
8
+ <li><%%= msg %></li>
9
+ <%% end %>
10
+ </ul>
11
+ </div>
12
+ <%% end %>
13
+ <div>
14
+ <%%= f.label :phrase %>
15
+ </div>
16
+ <div>
17
+ <%%= f.text_field :phrase %>
18
+ </div>
19
+ <div>
20
+ <%%= f.label :is_negative %>
21
+ </div>
22
+ <div>
23
+ <%%= f.check_box :is_negative %>
24
+ </div>
25
+ <div>
26
+ <%%= f.submit %> | <a href='<%%=<%=keyword.pluralize%>_path%>'>back</a>
27
+ </div>
28
+ <%%end%>
@@ -0,0 +1,2 @@
1
+ <h1>Edit Keyword</h1>
2
+ <%%= render 'form' %>
@@ -0,0 +1,14 @@
1
+ <h1>Keywords</h1>
2
+ <div class='menu'>
3
+ <a href='<%%=new_<%=keyword%>_path%>'>Add keyword</a>
4
+ </div>
5
+ <h2>Inclusive</h2>
6
+ <%%@positive.each do |keyword|%>
7
+ <div class='keyword'><%%=keyword.phrase%> | <a href='<%%=edit_<%=keyword%>_path keyword.id%>'>Edit</a>
8
+ </div>
9
+ <%%end%>
10
+ <h2>Exclusive</h2>
11
+ <%%@negative.each do |keyword|%>
12
+ <div class='keyword'><%%=keyword.phrase%> | <a href='<%%=edit_<%=keyword%>_path keyword.id%>'>Edit</a>
13
+ </div>
14
+ <%%end%>
@@ -0,0 +1,2 @@
1
+ <h1>New Keyword</h1>
2
+ <%%= render 'form' %>
@@ -0,0 +1,5 @@
1
+ <div class='menu'>
2
+ <a href='/<%= resource.pluralize %>'>Resources</a> |
3
+ <a href='/<%= news.pluralize %>'>News</a> |
4
+ <a href='/<%= keyword.pluralize %>'>Keywords</a> |
5
+ </div>
@@ -0,0 +1,11 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>WebFeed</title>
5
+ <%= stylesheet_link_tag "webfeed", :media => "all" %>
6
+ <%= csrf_meta_tags %>
7
+ </head>
8
+ <body class='daily'>
9
+ <%= yield %>
10
+ </body>
11
+ </html>
@@ -0,0 +1,16 @@
1
+ <h1>News</h1>
2
+ <%% @news.each do |news| %>
3
+ <div class='news <%%= 'published' if news.is_published %>'>
4
+ <h2><a href='<%%= "#{read_<%=news%>_path(news.id, news.title.gsub(/\W+/, '-'))}.html" %>'><%%= news.title %></a></h2>
5
+ <img src='<%%= news.image.url(:thumb) %>'/><p class='inline desc'><%%= news.description.html_safe %></p>
6
+ <%%unless news.is_published%>
7
+ <%%= form_tag publish_<%=news%>_path(news.id) %>
8
+ <button>Publish</button>
9
+ </form>
10
+ <%%else%>
11
+ <%%= form_tag unpublish_<%=news%>_path(news.id) %>
12
+ <button>Unpublish</button>
13
+ </form>
14
+ <%%end%>
15
+ </div>
16
+ <%%end%>
@@ -0,0 +1,9 @@
1
+ <div class='daily_header'>
2
+ <h1><a href='<%%= <%=news%>_path %>'>Read More News <span>@ WebFeed</span></a></h1>
3
+ <h2><a href='<%%=@news.url%>' target='_blank'><%%= @news.title %></a></h2>
4
+ <img src='<%%= @news.image.url(:thumb) %>'/>
5
+ <p class='inline desc'><%%= truncate @news.description, :length => 400 %></p>
6
+ </div>
7
+ <div class='daily_reader'>
8
+ <iframe frameborder='0' src='<%%=@news.url%>'></iframe>
9
+ </div>
@@ -0,0 +1,34 @@
1
+ <%%= form_for @resource do |f| %>
2
+ <%% if @resource.errors.any? %>
3
+ <div class="errors">
4
+ <h2><%%= pluralize(@resource.errors.count, "error") %> prohibited this resource from being saved:</h2>
5
+
6
+ <ul>
7
+ <%% @resource.errors.full_messages.each do |msg| %>
8
+ <li><%%= msg %></li>
9
+ <%% end %>
10
+ </ul>
11
+ </div>
12
+ <%% end %>
13
+ <div>
14
+ <%%= f.label :name %>
15
+ </div>
16
+ <div>
17
+ <%%= f.text_field :name %>
18
+ </div>
19
+ <div>
20
+ <%%= f.label :url %>
21
+ </div>
22
+ <div>
23
+ <%%= f.text_field :url %>
24
+ </div>
25
+ <div>
26
+ <%%= f.label :frequency %>
27
+ </div>
28
+ <div>
29
+ <%%= f.text_field :frequency %>
30
+ </div>
31
+ <div>
32
+ <%%= f.submit %> | <a href='<%%=<%=resource.pluralize%>_path%>'>back</a>
33
+ </div>
34
+ <%%end%>
@@ -0,0 +1,2 @@
1
+ <h1>Edit Resource</h1>
2
+ <%%= render 'form' %>
@@ -0,0 +1,29 @@
1
+ <h1>Resources</h1>
2
+ <div class='menu'>
3
+ <a href='<%%=new_<%=resource%>_path%>'>Add Resource</a>
4
+ </div>
5
+ <div>
6
+ <h2>Expired Resources</h2>
7
+ <%%@expired.each do |resource|%>
8
+ <div class='resource'>
9
+ <h3><%%=resource.name%></h3>
10
+ <h4><%%=resource.url%></h4>
11
+ <div class='frequency'>every <%%=resource.frequency%> minutes
12
+ <%%= form_tag read_<%=resource%>_path(resource.id) %>
13
+ <button>Update</button>
14
+ </form>
15
+ | <a href='<%%= edit_<%=resource%>_path resource.id %>'>Edit</a>
16
+ </div>
17
+ </div>
18
+ <%%end%>
19
+ <h2>Recently Checked Resources</h2>
20
+ <%%@uptodated.each do |resource|%>
21
+ <div class='resource'>
22
+ <h3><%%=resource.name%></h3>
23
+ <h4><%%=resource.url%></h4>
24
+ <div class='frequency'>every <%%=resource.frequency%> minutes
25
+ | <a href='<%%= edit_<%=resource%>_path resource.id %>'>Edit</a>
26
+ </div>
27
+ </div>
28
+ <%%end%>
29
+ </div>
@@ -0,0 +1,2 @@
1
+ <h1>New Resource</h1>
2
+ <%%= render 'form' %>
@@ -0,0 +1,4 @@
1
+ # desc "Explaining what the task does"
2
+ # task :webfeed do
3
+ # # Task goes here
4
+ # end
@@ -0,0 +1,3 @@
1
+ module Webfeed
2
+ VERSION = "0.0.1"
3
+ end
data/lib/webfeed.rb ADDED
@@ -0,0 +1,4 @@
1
+ require 'feed_reader'
2
+
3
+ module Webfeed
4
+ end
metadata ADDED
@@ -0,0 +1,201 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: webfeed
3
+ version: !ruby/object:Gem::Version
4
+ hash: 29
5
+ prerelease:
6
+ segments:
7
+ - 0
8
+ - 0
9
+ - 1
10
+ version: 0.0.1
11
+ platform: ruby
12
+ authors:
13
+ - Arash Karimzadeh
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2012-09-06 00:00:00 Z
19
+ dependencies:
20
+ - !ruby/object:Gem::Dependency
21
+ name: rails
22
+ prerelease: false
23
+ requirement: &id001 !ruby/object:Gem::Requirement
24
+ none: false
25
+ requirements:
26
+ - - ~>
27
+ - !ruby/object:Gem::Version
28
+ hash: 31
29
+ segments:
30
+ - 3
31
+ - 2
32
+ - 8
33
+ version: 3.2.8
34
+ type: :runtime
35
+ version_requirements: *id001
36
+ - !ruby/object:Gem::Dependency
37
+ name: mysql2
38
+ prerelease: false
39
+ requirement: &id002 !ruby/object:Gem::Requirement
40
+ none: false
41
+ requirements:
42
+ - - ">="
43
+ - !ruby/object:Gem::Version
44
+ hash: 3
45
+ segments:
46
+ - 0
47
+ version: "0"
48
+ type: :development
49
+ version_requirements: *id002
50
+ - !ruby/object:Gem::Dependency
51
+ name: rspec-rails
52
+ prerelease: false
53
+ requirement: &id003 !ruby/object:Gem::Requirement
54
+ none: false
55
+ requirements:
56
+ - - ">="
57
+ - !ruby/object:Gem::Version
58
+ hash: 3
59
+ segments:
60
+ - 0
61
+ version: "0"
62
+ type: :development
63
+ version_requirements: *id003
64
+ - !ruby/object:Gem::Dependency
65
+ name: capybara
66
+ prerelease: false
67
+ requirement: &id004 !ruby/object:Gem::Requirement
68
+ none: false
69
+ requirements:
70
+ - - ">="
71
+ - !ruby/object:Gem::Version
72
+ hash: 3
73
+ segments:
74
+ - 0
75
+ version: "0"
76
+ type: :development
77
+ version_requirements: *id004
78
+ - !ruby/object:Gem::Dependency
79
+ name: guard-rspec
80
+ prerelease: false
81
+ requirement: &id005 !ruby/object:Gem::Requirement
82
+ none: false
83
+ requirements:
84
+ - - ">="
85
+ - !ruby/object:Gem::Version
86
+ hash: 3
87
+ segments:
88
+ - 0
89
+ version: "0"
90
+ type: :development
91
+ version_requirements: *id005
92
+ - !ruby/object:Gem::Dependency
93
+ name: guard-spork
94
+ prerelease: false
95
+ requirement: &id006 !ruby/object:Gem::Requirement
96
+ none: false
97
+ requirements:
98
+ - - ">="
99
+ - !ruby/object:Gem::Version
100
+ hash: 3
101
+ segments:
102
+ - 0
103
+ version: "0"
104
+ type: :development
105
+ version_requirements: *id006
106
+ - !ruby/object:Gem::Dependency
107
+ name: rb-inotify
108
+ prerelease: false
109
+ requirement: &id007 !ruby/object:Gem::Requirement
110
+ none: false
111
+ requirements:
112
+ - - ~>
113
+ - !ruby/object:Gem::Version
114
+ hash: 47
115
+ segments:
116
+ - 0
117
+ - 8
118
+ - 8
119
+ version: 0.8.8
120
+ type: :development
121
+ version_requirements: *id007
122
+ description: Read feeds from all around the world and publish them within your website
123
+ email:
124
+ - arash@tectual.com.au
125
+ executables: []
126
+
127
+ extensions: []
128
+
129
+ extra_rdoc_files: []
130
+
131
+ files:
132
+ - lib/tasks/webfeed_tasks.rake
133
+ - lib/webfeed/version.rb
134
+ - lib/generators/web_feed/add_image_generator.rb
135
+ - lib/generators/web_feed/keyword_generator.rb
136
+ - lib/generators/web_feed/install_generator.rb
137
+ - lib/generators/web_feed/templates/models/news.rb.erb
138
+ - lib/generators/web_feed/templates/models/resource.rb.erb
139
+ - lib/generators/web_feed/templates/models/keyword.rb.erb
140
+ - lib/generators/web_feed/templates/migrations/create_keywords.rb.erb
141
+ - lib/generators/web_feed/templates/migrations/create_resources.rb.erb
142
+ - lib/generators/web_feed/templates/migrations/add_attachment_image_to_news.rb.erb
143
+ - lib/generators/web_feed/templates/migrations/create_news.rb.erb
144
+ - lib/generators/web_feed/templates/controllers/keywords_controller.rb.erb
145
+ - lib/generators/web_feed/templates/controllers/resources_controller.rb.erb
146
+ - lib/generators/web_feed/templates/controllers/news_controller.rb.erb
147
+ - lib/generators/web_feed/templates/views/layouts/_webfeed.html.erb
148
+ - lib/generators/web_feed/templates/views/layouts/webfeed.html.erb
149
+ - lib/generators/web_feed/templates/views/news/show.html.erb
150
+ - lib/generators/web_feed/templates/views/news/index.html.erb
151
+ - lib/generators/web_feed/templates/views/keywords/index.html.erb
152
+ - lib/generators/web_feed/templates/views/keywords/_form.html.erb
153
+ - lib/generators/web_feed/templates/views/keywords/edit.html.erb
154
+ - lib/generators/web_feed/templates/views/keywords/new.html.erb
155
+ - lib/generators/web_feed/templates/views/resources/index.html.erb
156
+ - lib/generators/web_feed/templates/views/resources/_form.html.erb
157
+ - lib/generators/web_feed/templates/views/resources/edit.html.erb
158
+ - lib/generators/web_feed/templates/views/resources/new.html.erb
159
+ - lib/generators/web_feed/templates/stylesheets/webfeed.css
160
+ - lib/generators/web_feed/resource_generator.rb
161
+ - lib/generators/web_feed/news_generator.rb
162
+ - lib/webfeed.rb
163
+ - lib/feed_reader.rb
164
+ - MIT-LICENSE
165
+ - Rakefile
166
+ - README.rdoc
167
+ homepage: https://github.com/tectual/WebFeed
168
+ licenses: []
169
+
170
+ post_install_message:
171
+ rdoc_options: []
172
+
173
+ require_paths:
174
+ - lib
175
+ required_ruby_version: !ruby/object:Gem::Requirement
176
+ none: false
177
+ requirements:
178
+ - - ">="
179
+ - !ruby/object:Gem::Version
180
+ hash: 3
181
+ segments:
182
+ - 0
183
+ version: "0"
184
+ required_rubygems_version: !ruby/object:Gem::Requirement
185
+ none: false
186
+ requirements:
187
+ - - ">="
188
+ - !ruby/object:Gem::Version
189
+ hash: 3
190
+ segments:
191
+ - 0
192
+ version: "0"
193
+ requirements: []
194
+
195
+ rubyforge_project:
196
+ rubygems_version: 1.8.21
197
+ signing_key:
198
+ specification_version: 3
199
+ summary: Read feeds and republish from your website
200
+ test_files: []
201
+