elasticsearch-persistence 0.1.3 → 0.1.4
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 +8 -8
- data/CHANGELOG.md +4 -0
- data/README.md +238 -7
- data/elasticsearch-persistence.gemspec +4 -1
- data/examples/music/album.rb +34 -0
- data/examples/music/artist.rb +50 -0
- data/examples/music/artists/_form.html.erb +8 -0
- data/examples/music/artists/artists_controller.rb +67 -0
- data/examples/music/artists/artists_controller_test.rb +53 -0
- data/examples/music/artists/index.html.erb +57 -0
- data/examples/music/artists/show.html.erb +51 -0
- data/examples/music/assets/application.css +226 -0
- data/examples/music/assets/autocomplete.css +48 -0
- data/examples/music/assets/blank_cover.png +0 -0
- data/examples/music/assets/form.css +113 -0
- data/examples/music/index_manager.rb +60 -0
- data/examples/music/search/index.html.erb +93 -0
- data/examples/music/search/search_controller.rb +41 -0
- data/examples/music/search/search_controller_test.rb +9 -0
- data/examples/music/search/search_helper.rb +15 -0
- data/examples/music/suggester.rb +45 -0
- data/examples/music/template.rb +392 -0
- data/examples/music/vendor/assets/jquery-ui-1.10.4.custom.min.css +7 -0
- data/examples/music/vendor/assets/jquery-ui-1.10.4.custom.min.js +6 -0
- data/examples/{sinatra → notes}/.gitignore +0 -0
- data/examples/{sinatra → notes}/Gemfile +0 -0
- data/examples/{sinatra → notes}/README.markdown +0 -0
- data/examples/{sinatra → notes}/application.rb +0 -0
- data/examples/{sinatra → notes}/config.ru +0 -0
- data/examples/{sinatra → notes}/test.rb +0 -0
- data/lib/elasticsearch/persistence.rb +19 -0
- data/lib/elasticsearch/persistence/model.rb +129 -0
- data/lib/elasticsearch/persistence/model/base.rb +75 -0
- data/lib/elasticsearch/persistence/model/errors.rb +8 -0
- data/lib/elasticsearch/persistence/model/find.rb +171 -0
- data/lib/elasticsearch/persistence/model/rails.rb +39 -0
- data/lib/elasticsearch/persistence/model/store.rb +239 -0
- data/lib/elasticsearch/persistence/model/utils.rb +0 -0
- data/lib/elasticsearch/persistence/repository.rb +3 -1
- data/lib/elasticsearch/persistence/repository/search.rb +25 -0
- data/lib/elasticsearch/persistence/version.rb +1 -1
- data/lib/rails/generators/elasticsearch/model/model_generator.rb +21 -0
- data/lib/rails/generators/elasticsearch/model/templates/model.rb.tt +9 -0
- data/lib/rails/generators/elasticsearch_generator.rb +2 -0
- data/test/integration/model/model_basic_test.rb +157 -0
- data/test/integration/repository/default_class_test.rb +6 -0
- data/test/unit/model_base_test.rb +40 -0
- data/test/unit/model_find_test.rb +147 -0
- data/test/unit/model_gateway_test.rb +99 -0
- data/test/unit/model_rails_test.rb +88 -0
- data/test/unit/model_store_test.rb +493 -0
- data/test/unit/repository_search_test.rb +17 -0
- metadata +79 -9
@@ -0,0 +1,60 @@
|
|
1
|
+
require 'open-uri'
|
2
|
+
|
3
|
+
class IndexManager
|
4
|
+
def self.create_index(options={})
|
5
|
+
client = Artist.gateway.client
|
6
|
+
index_name = Artist.index_name
|
7
|
+
|
8
|
+
client.indices.delete index: index_name rescue nil if options[:force]
|
9
|
+
|
10
|
+
settings = Artist.settings.to_hash.merge(Album.settings.to_hash)
|
11
|
+
mappings = Artist.mappings.to_hash.merge(Album.mappings.to_hash)
|
12
|
+
|
13
|
+
client.indices.create index: index_name,
|
14
|
+
body: {
|
15
|
+
settings: settings.to_hash,
|
16
|
+
mappings: mappings.to_hash }
|
17
|
+
end
|
18
|
+
|
19
|
+
def self.import_from_yaml(source, options={})
|
20
|
+
create_index force: true if options[:force]
|
21
|
+
|
22
|
+
input = open(source)
|
23
|
+
artists = YAML.load_documents input
|
24
|
+
|
25
|
+
artists.each do |artist|
|
26
|
+
Artist.create artist.update(
|
27
|
+
'album_count' => artist['releases'].size,
|
28
|
+
'members_combined' => artist['members'].join(', '),
|
29
|
+
'suggest_name' => {
|
30
|
+
'input' => artist['namevariations'].unshift(artist['name']),
|
31
|
+
'output' => artist['name'],
|
32
|
+
'payload' => { 'url' => "/artists/#{artist['id']}" }
|
33
|
+
},
|
34
|
+
'suggest_member' => {
|
35
|
+
'input' => artist['members'],
|
36
|
+
'output' => artist['name'],
|
37
|
+
'payload' => { 'url' => "/artists/#{artist['id']}" }
|
38
|
+
}
|
39
|
+
)
|
40
|
+
|
41
|
+
artist['releases'].each do |album|
|
42
|
+
album.update(
|
43
|
+
'suggest_title' => {
|
44
|
+
'input' => album['title'],
|
45
|
+
'output' => album['title'],
|
46
|
+
'payload' => { 'url' => "/artists/#{artist['id']}#album_#{album['id']}" }
|
47
|
+
},
|
48
|
+
'suggest_track' => {
|
49
|
+
'input' => album['tracklist'].map { |d| d['title'] },
|
50
|
+
'output' => album['title'],
|
51
|
+
'payload' => { 'url' => "/artists/#{artist['id']}#album_#{album['id']}" }
|
52
|
+
}
|
53
|
+
)
|
54
|
+
album['notes'] = album['notes'].to_s.gsub(/<.+?>/, '').gsub(/ {2,}/, '')
|
55
|
+
album['released'] = nil if album['released'] < 1
|
56
|
+
Album.create album, id: album['id'], parent: artist['id']
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -0,0 +1,93 @@
|
|
1
|
+
<header>
|
2
|
+
<h1>
|
3
|
+
<span class="back"><%= link_to "〈".html_safe, :back, title: "Back" %></span>
|
4
|
+
Artists & Albums
|
5
|
+
</h1>
|
6
|
+
</header>
|
7
|
+
|
8
|
+
<section id="searchbox">
|
9
|
+
<%= form_tag search_path, method: 'get' do %>
|
10
|
+
<input type="text" name="q" value="<%= params[:q] %>" id="q" autofocus="autofocus" placeholder="start typing to search..." tabindex="0" />
|
11
|
+
<% end %>
|
12
|
+
</section>
|
13
|
+
|
14
|
+
<section class="artists">
|
15
|
+
<% @artists.each do |artist| %>
|
16
|
+
<%= content_tag :div, class: 'result clearfix' do %>
|
17
|
+
<h2>
|
18
|
+
<%= link_to artist do %>
|
19
|
+
<span class="name"><%= highlighted(artist, :name) %></span>
|
20
|
+
<small><%= pluralize artist.album_count, 'album' %></small>
|
21
|
+
<% end %>
|
22
|
+
</h2>
|
23
|
+
<% if highlight = highlight(artist, :members_combined) %>
|
24
|
+
<p class="small">
|
25
|
+
<span class="label">Members</span>
|
26
|
+
<%= highlight.first.html_safe %>
|
27
|
+
</p>
|
28
|
+
<% end %>
|
29
|
+
<% if highlight = highlight(artist, :profile) %>
|
30
|
+
<p class="small">
|
31
|
+
<span class="label">Profile</span>
|
32
|
+
<%= highlight.join('…').html_safe %>
|
33
|
+
</p>
|
34
|
+
<% end %>
|
35
|
+
<% end %>
|
36
|
+
<% end %>
|
37
|
+
</section>
|
38
|
+
|
39
|
+
<section class="albums">
|
40
|
+
<% @albums.each do |album| %>
|
41
|
+
<%= content_tag :div, class: 'result clearfix' do %>
|
42
|
+
<h2>
|
43
|
+
<%= link_to artist_path(album.artist_id, anchor: "album_#{album.id}") do %>
|
44
|
+
<span class="name"><%= highlighted(album, :title) %></span>
|
45
|
+
<small><%= album.artist %></small>
|
46
|
+
<small>(<%= [album.meta.formats.first, album.released].compact.join(' ') %>)</small>
|
47
|
+
<% end %>
|
48
|
+
</h2>
|
49
|
+
|
50
|
+
<% if highlight = highlight(album, 'tracklist.title') %>
|
51
|
+
<p class="small">
|
52
|
+
<span class="label">Tracks</span>
|
53
|
+
<%= highlight.join('…').html_safe %>
|
54
|
+
</p>
|
55
|
+
<% end %>
|
56
|
+
|
57
|
+
<% if highlight = highlight(album, :notes) %>
|
58
|
+
<p class="small">
|
59
|
+
<span class="label">Notes</span>
|
60
|
+
<%= highlight.map { |d| d.gsub(/^\.\s?/, '') }.join('…').html_safe %>
|
61
|
+
</p>
|
62
|
+
<% end %>
|
63
|
+
<% end %>
|
64
|
+
<% end %>
|
65
|
+
</section>
|
66
|
+
|
67
|
+
<% if @artists.empty? && @albums.empty? %>
|
68
|
+
<section class="no-results">
|
69
|
+
<p>The search hasn't returned any results...</p>
|
70
|
+
</section>
|
71
|
+
<% end %>
|
72
|
+
|
73
|
+
<script>
|
74
|
+
$.widget( "custom.suggest", $.ui.autocomplete, {
|
75
|
+
_renderMenu: function( ul, items ) {
|
76
|
+
$.each( items, function( index, item ) {
|
77
|
+
var category = ul.append( "<li class='ui-autocomplete-category'>" + item.label + "</li>" );
|
78
|
+
|
79
|
+
$.each( item.value, function( index, item ) {
|
80
|
+
var li = $('<li class="ui-autocomplete-item"><a href="<%= Rails.application.config.relative_url_root %>'+ item.payload.url +'">'+ item.text +'</a></li>').data('ui-autocomplete-item', item )
|
81
|
+
category.append(li)
|
82
|
+
} )
|
83
|
+
});
|
84
|
+
}
|
85
|
+
});
|
86
|
+
|
87
|
+
$( "#q" ).suggest({
|
88
|
+
source: '<%= suggest_path %>',
|
89
|
+
select: function(event, ui) {
|
90
|
+
document.location.href = '<%= Rails.application.config.relative_url_root %>'+ui.item.payload.url
|
91
|
+
}
|
92
|
+
});
|
93
|
+
</script>
|
@@ -0,0 +1,41 @@
|
|
1
|
+
class SearchController < ApplicationController
|
2
|
+
|
3
|
+
def index
|
4
|
+
tags = { pre_tags: '<em class="hl">', post_tags: '</em>' }
|
5
|
+
@artists = Artist.search \
|
6
|
+
query: {
|
7
|
+
multi_match: {
|
8
|
+
query: params[:q],
|
9
|
+
fields: ['name^10','members^2','profile']
|
10
|
+
}
|
11
|
+
},
|
12
|
+
highlight: {
|
13
|
+
tags_schema: 'styled',
|
14
|
+
fields: {
|
15
|
+
name: { number_of_fragments: 0 },
|
16
|
+
members_combined: { number_of_fragments: 0 },
|
17
|
+
profile: { fragment_size: 50 }
|
18
|
+
}
|
19
|
+
}
|
20
|
+
|
21
|
+
@albums = Album.search \
|
22
|
+
query: {
|
23
|
+
multi_match: {
|
24
|
+
query: params[:q],
|
25
|
+
fields: ['title^100','tracklist.title^10','notes^1']
|
26
|
+
}
|
27
|
+
},
|
28
|
+
highlight: {
|
29
|
+
tags_schema: 'styled',
|
30
|
+
fields: {
|
31
|
+
title: { number_of_fragments: 0 },
|
32
|
+
'tracklist.title' => { number_of_fragments: 0 },
|
33
|
+
notes: { fragment_size: 50 }
|
34
|
+
}
|
35
|
+
}
|
36
|
+
end
|
37
|
+
|
38
|
+
def suggest
|
39
|
+
render json: Suggester.new(params)
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module SearchHelper
|
2
|
+
|
3
|
+
def highlight(object, field)
|
4
|
+
object.try(:hit).try(:highlight).try(field)
|
5
|
+
end
|
6
|
+
|
7
|
+
def highlighted(object, field)
|
8
|
+
if h = object.try(:hit).try(:highlight).try(field).try(:first)
|
9
|
+
h.html_safe
|
10
|
+
else
|
11
|
+
field.to_s.split('.').reduce(object) { |result,item| result.try(item) }
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
class Suggester
|
2
|
+
attr_reader :response
|
3
|
+
|
4
|
+
def initialize(params={})
|
5
|
+
@term = params[:term]
|
6
|
+
end
|
7
|
+
|
8
|
+
def response
|
9
|
+
@response ||= begin
|
10
|
+
Elasticsearch::Persistence.client.suggest \
|
11
|
+
index: Artist.index_name,
|
12
|
+
body: {
|
13
|
+
artists: {
|
14
|
+
text: @term,
|
15
|
+
completion: { field: 'suggest_name' }
|
16
|
+
},
|
17
|
+
members: {
|
18
|
+
text: @term,
|
19
|
+
completion: { field: 'suggest_member' }
|
20
|
+
},
|
21
|
+
albums: {
|
22
|
+
text: @term,
|
23
|
+
completion: { field: 'suggest_title' }
|
24
|
+
},
|
25
|
+
tracks: {
|
26
|
+
text: @term,
|
27
|
+
completion: { field: 'suggest_track' }
|
28
|
+
}
|
29
|
+
}
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def as_json(options={})
|
34
|
+
response
|
35
|
+
.except('_shards')
|
36
|
+
.reduce([]) do |sum,d|
|
37
|
+
# category = { d.first => d.second.first['options'] }
|
38
|
+
item = { :label => d.first.titleize, :value => d.second.first['options'] }
|
39
|
+
sum << item
|
40
|
+
end
|
41
|
+
.reject do |d|
|
42
|
+
d[:value].empty?
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,392 @@
|
|
1
|
+
# ======================================================================================
|
2
|
+
# Template for generating a Rails application with support for Elasticsearch persistence
|
3
|
+
# ======================================================================================
|
4
|
+
#
|
5
|
+
# This file creates a fully working Rails application with support for storing and retrieving models
|
6
|
+
# in Elasticsearch, using the `elasticsearch-persistence` gem
|
7
|
+
# (https://github.com/elasticsearch/elasticsearch-rails/tree/persistence-model/elasticsearch-persistence).
|
8
|
+
#
|
9
|
+
# Requirements:
|
10
|
+
# -------------
|
11
|
+
#
|
12
|
+
# * Git
|
13
|
+
# * Ruby >= 1.9.3
|
14
|
+
# * Rails >= 4
|
15
|
+
# * Java >= 7 (for Elasticsearch)
|
16
|
+
#
|
17
|
+
# Usage:
|
18
|
+
# ------
|
19
|
+
#
|
20
|
+
# $ time rails new music --force --skip --skip-bundle --skip-active-record --template /Users/karmi/Contracts/Elasticsearch/Projects/Clients/Ruby/elasticsearch-rails/elasticsearch-persistence/examples/music/template.rb
|
21
|
+
#
|
22
|
+
# =====================================================================================================
|
23
|
+
|
24
|
+
STDOUT.sync = true
|
25
|
+
STDERR.sync = true
|
26
|
+
|
27
|
+
require 'uri'
|
28
|
+
require 'net/http'
|
29
|
+
|
30
|
+
at_exit do
|
31
|
+
pid = File.read("#{destination_root}/tmp/pids/elasticsearch.pid") rescue nil
|
32
|
+
if pid
|
33
|
+
say_status "Stop", "Elasticsearch", :yellow
|
34
|
+
run "kill #{pid}"
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
run "touch tmp/.gitignore"
|
39
|
+
|
40
|
+
append_to_file ".gitignore", "vendor/elasticsearch-1.2.1/\n"
|
41
|
+
|
42
|
+
git :init
|
43
|
+
git add: "."
|
44
|
+
git commit: "-m 'Initial commit: Clean application'"
|
45
|
+
|
46
|
+
# ----- Download Elasticsearch --------------------------------------------------------------------
|
47
|
+
|
48
|
+
unless (Net::HTTP.get(URI.parse('http://localhost:9200')) rescue false)
|
49
|
+
COMMAND = <<-COMMAND.gsub(/^ /, '')
|
50
|
+
curl -# -O "http://download.elasticsearch.org/elasticsearch/elasticsearch/elasticsearch-1.2.1.tar.gz"
|
51
|
+
tar -zxf elasticsearch-1.2.1.tar.gz
|
52
|
+
rm -f elasticsearch-1.2.1.tar.gz
|
53
|
+
./elasticsearch-1.2.1/bin/elasticsearch -d -p #{destination_root}/tmp/pids/elasticsearch.pid
|
54
|
+
COMMAND
|
55
|
+
|
56
|
+
puts "\n"
|
57
|
+
say_status "ERROR", "Elasticsearch not running!\n", :red
|
58
|
+
puts '-'*80
|
59
|
+
say_status '', "It appears that Elasticsearch is not running on this machine."
|
60
|
+
say_status '', "Is it installed? Do you want me to install it for you with this command?\n\n"
|
61
|
+
COMMAND.each_line { |l| say_status '', "$ #{l}" }
|
62
|
+
puts
|
63
|
+
say_status '', "(To uninstall, just remove the generated application directory.)"
|
64
|
+
puts '-'*80, ''
|
65
|
+
|
66
|
+
if yes?("Install Elasticsearch?", :bold)
|
67
|
+
puts
|
68
|
+
say_status "Install", "Elasticsearch", :yellow
|
69
|
+
|
70
|
+
java_info = `java -version 2>&1`
|
71
|
+
|
72
|
+
unless java_info.match /1\.[7-9]/
|
73
|
+
puts
|
74
|
+
say_status "ERROR", "Required Java version (1.7) not found, exiting...", :red
|
75
|
+
exit(1)
|
76
|
+
end
|
77
|
+
|
78
|
+
commands = COMMAND.split("\n")
|
79
|
+
exec = commands.pop
|
80
|
+
inside("vendor") do
|
81
|
+
commands.each { |command| run command }
|
82
|
+
run "(#{exec})" # Launch Elasticsearch in subshell
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end unless ENV['RAILS_NO_ES_INSTALL']
|
86
|
+
|
87
|
+
# ----- Add README --------------------------------------------------------------------------------
|
88
|
+
|
89
|
+
puts
|
90
|
+
say_status "README", "Adding Readme...\n", :yellow
|
91
|
+
puts '-'*80, ''; sleep 0.25
|
92
|
+
|
93
|
+
remove_file 'README.rdoc'
|
94
|
+
|
95
|
+
create_file 'README.rdoc', <<-README
|
96
|
+
= Ruby on Rails and Elasticsearch persistence: Example application
|
97
|
+
|
98
|
+
README
|
99
|
+
|
100
|
+
|
101
|
+
git add: "."
|
102
|
+
git commit: "-m 'Added README for the application'"
|
103
|
+
|
104
|
+
# ----- Use Thin ----------------------------------------------------------------------------------
|
105
|
+
|
106
|
+
begin
|
107
|
+
require 'thin'
|
108
|
+
puts
|
109
|
+
say_status "Rubygems", "Adding Thin into Gemfile...\n", :yellow
|
110
|
+
puts '-'*80, '';
|
111
|
+
|
112
|
+
gem 'thin'
|
113
|
+
rescue LoadError
|
114
|
+
end
|
115
|
+
|
116
|
+
# ----- Auxiliary gems ----------------------------------------------------------------------------
|
117
|
+
|
118
|
+
# ----- Remove CoffeeScript, Sass and "all that jazz" ---------------------------------------------
|
119
|
+
|
120
|
+
comment_lines 'Gemfile', /gem 'coffee/
|
121
|
+
comment_lines 'Gemfile', /gem 'sass/
|
122
|
+
comment_lines 'Gemfile', /gem 'uglifier/
|
123
|
+
uncomment_lines 'Gemfile', /gem 'therubyracer/
|
124
|
+
|
125
|
+
# ----- Add gems into Gemfile ---------------------------------------------------------------------
|
126
|
+
|
127
|
+
puts
|
128
|
+
say_status "Rubygems", "Adding Elasticsearch libraries into Gemfile...\n", :yellow
|
129
|
+
puts '-'*80, ''; sleep 0.75
|
130
|
+
|
131
|
+
gem "quiet_assets"
|
132
|
+
gem "simple_form"
|
133
|
+
|
134
|
+
gem 'elasticsearch', git: 'git://github.com/elasticsearch/elasticsearch-ruby.git'
|
135
|
+
gem 'elasticsearch-persistence', git: 'git://github.com/elasticsearch/elasticsearch-rails.git', branch: 'persistence-model', require: 'elasticsearch/persistence/model'
|
136
|
+
gem 'elasticsearch-rails', git: 'git://github.com/elasticsearch/elasticsearch-rails.git'
|
137
|
+
|
138
|
+
git add: "Gemfile*"
|
139
|
+
git commit: "-m 'Added libraries into Gemfile'"
|
140
|
+
|
141
|
+
# ----- Install gems ------------------------------------------------------------------------------
|
142
|
+
|
143
|
+
puts
|
144
|
+
say_status "Rubygems", "Installing Rubygems...", :yellow
|
145
|
+
puts '-'*80, ''
|
146
|
+
|
147
|
+
run "bundle install"
|
148
|
+
|
149
|
+
# ----- Autoload ./lib ----------------------------------------------------------------------------
|
150
|
+
|
151
|
+
puts
|
152
|
+
say_status "Application", "Adding autoloading of ./lib...", :yellow
|
153
|
+
puts '-'*80, ''
|
154
|
+
|
155
|
+
insert_into_file 'config/application.rb',
|
156
|
+
'
|
157
|
+
config.autoload_paths += %W(#{config.root}/lib)
|
158
|
+
|
159
|
+
',
|
160
|
+
after: 'class Application < Rails::Application'
|
161
|
+
|
162
|
+
git commit: "-a -m 'Added autoloading of the ./lib folder'"
|
163
|
+
|
164
|
+
# ----- Add jQuery UI ----------------------------------------------------------------------------
|
165
|
+
|
166
|
+
puts
|
167
|
+
say_status "Assets", "Adding jQuery UI...", :yellow
|
168
|
+
puts '-'*80, ''; sleep 0.25
|
169
|
+
|
170
|
+
if ENV['LOCAL']
|
171
|
+
copy_file File.expand_path('../vendor/assets/jquery-ui-1.10.4.custom.min.js', __FILE__),
|
172
|
+
'vendor/assets/javascripts/jquery-ui-1.10.4.custom.min.js'
|
173
|
+
copy_file File.expand_path('../vendor/assets/jquery-ui-1.10.4.custom.min.css', __FILE__),
|
174
|
+
'vendor/assets/stylesheets/ui-lightness/jquery-ui-1.10.4.custom.min.css'
|
175
|
+
else
|
176
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/vendor/assets/jquery-ui-1.10.4.custom.min.js',
|
177
|
+
'vendor/assets/javascripts/jquery-ui-1.10.4.custom.min.js'
|
178
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/vendor/assets/jquery-ui-1.10.4.custom.min.css',
|
179
|
+
'vendor/assets/stylesheets/ui-lightness/jquery-ui-1.10.4.custom.min.css'
|
180
|
+
end
|
181
|
+
|
182
|
+
append_to_file 'app/assets/javascripts/application.js', "//= require jquery-ui-1.10.4.custom.min.js"
|
183
|
+
|
184
|
+
git commit: "-a -m 'Added jQuery UI'"
|
185
|
+
|
186
|
+
# ----- Generate Artist scaffold ------------------------------------------------------------------
|
187
|
+
|
188
|
+
puts
|
189
|
+
say_status "Model", "Generating the Artist scaffold...", :yellow
|
190
|
+
puts '-'*80, ''; sleep 0.25
|
191
|
+
|
192
|
+
generate :scaffold, "Artist name:String --orm=elasticsearch"
|
193
|
+
route "root to: 'artists#index'"
|
194
|
+
|
195
|
+
git add: "."
|
196
|
+
git commit: "-m 'Added the generated Artist scaffold'"
|
197
|
+
|
198
|
+
# ----- Generate Album model ----------------------------------------------------------------------
|
199
|
+
|
200
|
+
puts
|
201
|
+
say_status "Model", "Generating the Album model...", :yellow
|
202
|
+
puts '-'*80, ''; sleep 0.25
|
203
|
+
|
204
|
+
generate :model, "Album --orm=elasticsearch"
|
205
|
+
|
206
|
+
git add: "."
|
207
|
+
git commit: "-m 'Added the generated Album model'"
|
208
|
+
|
209
|
+
# ----- Add proper model classes ------------------------------------------------------------------
|
210
|
+
|
211
|
+
puts
|
212
|
+
say_status "Model", "Adding Album, Artist and Suggester models implementation...", :yellow
|
213
|
+
puts '-'*80, ''; sleep 0.25
|
214
|
+
|
215
|
+
if ENV['LOCAL']
|
216
|
+
copy_file File.expand_path('../artist.rb', __FILE__), 'app/models/artist.rb'
|
217
|
+
copy_file File.expand_path('../album.rb', __FILE__), 'app/models/album.rb'
|
218
|
+
copy_file File.expand_path('../suggester.rb', __FILE__), 'app/models/suggester.rb'
|
219
|
+
else
|
220
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artist.rb',
|
221
|
+
'app/models/artist.rb'
|
222
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/album.rb',
|
223
|
+
'app/models/album.rb'
|
224
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/suggester.rb',
|
225
|
+
'app/models/suggester.rb'
|
226
|
+
end
|
227
|
+
|
228
|
+
git add: "./app/models"
|
229
|
+
git commit: "-m 'Added Album, Artist and Suggester models implementation'"
|
230
|
+
|
231
|
+
# ----- Add controllers and views -----------------------------------------------------------------
|
232
|
+
|
233
|
+
puts
|
234
|
+
say_status "Views", "Adding ArtistsController and views...", :yellow
|
235
|
+
puts '-'*80, ''; sleep 0.25
|
236
|
+
|
237
|
+
if ENV['LOCAL']
|
238
|
+
copy_file File.expand_path('../artists/artists_controller.rb', __FILE__), 'app/controllers/artists_controller.rb'
|
239
|
+
copy_file File.expand_path('../artists/index.html.erb', __FILE__), 'app/views/artists/index.html.erb'
|
240
|
+
copy_file File.expand_path('../artists/show.html.erb', __FILE__), 'app/views/artists/show.html.erb'
|
241
|
+
copy_file File.expand_path('../artists/_form.html.erb', __FILE__), 'app/views/artists/_form.html.erb'
|
242
|
+
copy_file File.expand_path('../artists/artists_controller_test.rb', __FILE__),
|
243
|
+
'test/controllers/artists_controller_test.rb'
|
244
|
+
else
|
245
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artists/artists_controller.rb',
|
246
|
+
'app/controllers/artists_controller.rb'
|
247
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artists/index.html.erb',
|
248
|
+
'app/views/artists/index.html.erb'
|
249
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artists/show.html.erb',
|
250
|
+
'app/views/artists/show.html.erb'
|
251
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artists/_form.html.erb',
|
252
|
+
'app/views/artists/_form.html.erb'
|
253
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/artists/artists_controller_test.rb',
|
254
|
+
'test/controllers/artists_controller_test.rb'
|
255
|
+
end
|
256
|
+
|
257
|
+
git commit: "-a -m 'Added ArtistsController and related views'"
|
258
|
+
|
259
|
+
puts
|
260
|
+
say_status "Views", "Adding SearchController and views...", :yellow
|
261
|
+
puts '-'*80, ''; sleep 0.25
|
262
|
+
|
263
|
+
if ENV['LOCAL']
|
264
|
+
copy_file File.expand_path('../search/search_controller.rb', __FILE__), 'app/controllers/search_controller.rb'
|
265
|
+
copy_file File.expand_path('../search/search_helper.rb', __FILE__), 'app/helpers/search_helper.rb'
|
266
|
+
copy_file File.expand_path('../search/index.html.erb', __FILE__), 'app/views/search/index.html.erb'
|
267
|
+
copy_file File.expand_path('../search/search_controller_test.rb', __FILE__),
|
268
|
+
'test/controllers/search_controller_test.rb'
|
269
|
+
else
|
270
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/search/search_controller.rb',
|
271
|
+
'app/controllers/search_controller.rb'
|
272
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/search/search_helper.rb',
|
273
|
+
'app/helpers/search_helper.rb'
|
274
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/search/index.html.erb',
|
275
|
+
'app/views/search/index.html.erb'
|
276
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/search/search_controller_test.rb',
|
277
|
+
'test/controllers/search_controller_test.rb'
|
278
|
+
end
|
279
|
+
|
280
|
+
route "get 'search', to: 'search#index'"
|
281
|
+
route "get 'suggest', to: 'search#suggest'"
|
282
|
+
|
283
|
+
comment_lines 'test/test_helper.rb', /fixtures \:all/
|
284
|
+
|
285
|
+
git add: "."
|
286
|
+
git commit: "-m 'Added SearchController and related views'"
|
287
|
+
|
288
|
+
# ----- Add assets -----------------------------------------------------------------
|
289
|
+
|
290
|
+
puts
|
291
|
+
say_status "Views", "Adding application assets...", :yellow
|
292
|
+
puts '-'*80, ''; sleep 0.25
|
293
|
+
|
294
|
+
git rm: 'app/assets/stylesheets/scaffold.css'
|
295
|
+
|
296
|
+
gsub_file 'app/views/layouts/application.html.erb', /<body>/, '<body class="<%= controller.action_name %>">'
|
297
|
+
|
298
|
+
if ENV['LOCAL']
|
299
|
+
copy_file File.expand_path('../assets/application.css', __FILE__), 'app/assets/stylesheets/application.css'
|
300
|
+
copy_file File.expand_path('../assets/autocomplete.css', __FILE__), 'app/assets/stylesheets/autocomplete.css'
|
301
|
+
copy_file File.expand_path('../assets/form.css', __FILE__), 'app/assets/stylesheets/form.css'
|
302
|
+
copy_file File.expand_path('../assets/blank_cover.png', __FILE__), 'public/images/blank_cover.png'
|
303
|
+
else
|
304
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/assets/application.css',
|
305
|
+
'app/assets/stylesheets/application.css'
|
306
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/assets/autocomplete.css',
|
307
|
+
'app/assets/stylesheets/autocomplete.css'
|
308
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/assets/form.css',
|
309
|
+
'app/assets/stylesheets/form.css'
|
310
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/assets/blank_cover.png',
|
311
|
+
'public/images/blank_cover.png'
|
312
|
+
end
|
313
|
+
|
314
|
+
git add: "."
|
315
|
+
git commit: "-m 'Added application assets'"
|
316
|
+
|
317
|
+
# ----- Add an Elasticsearch initializer ----------------------------------------------------------
|
318
|
+
|
319
|
+
puts
|
320
|
+
say_status "Initializer", "Adding an Elasticsearch initializer...", :yellow
|
321
|
+
puts '-'*80, ''; sleep 0.25
|
322
|
+
|
323
|
+
initializer 'elasticsearch.rb', %q{
|
324
|
+
Elasticsearch::Persistence.client = Elasticsearch::Client.new host: ENV['ELASTICSEARCH_URL'] || 'localhost:9200'
|
325
|
+
|
326
|
+
if Rails.env.development?
|
327
|
+
logger = ActiveSupport::Logger.new(STDERR)
|
328
|
+
logger.level = Logger::INFO
|
329
|
+
logger.formatter = proc { |s, d, p, m| "\e[2m#{m}\n\e[0m" }
|
330
|
+
Elasticsearch::Persistence.client.transport.logger = logger
|
331
|
+
end
|
332
|
+
}.gsub(/^ /, '')
|
333
|
+
|
334
|
+
git add: "./config"
|
335
|
+
git commit: "-m 'Added an Elasticsearch initializer'"
|
336
|
+
|
337
|
+
# ----- Add IndexManager -----------------------------------------------------------------
|
338
|
+
|
339
|
+
puts
|
340
|
+
say_status "Application", "Adding the IndexManager class...", :yellow
|
341
|
+
puts '-'*80, ''; sleep 0.25
|
342
|
+
|
343
|
+
if ENV['LOCAL']
|
344
|
+
copy_file File.expand_path('../index_manager.rb', __FILE__), 'lib/index_manager.rb'
|
345
|
+
else
|
346
|
+
get 'https://raw.githubusercontent.com/elasticsearch/elasticsearch-rails/persistence-model/elasticsearch-persistence/examples/music/index_manager.rb',
|
347
|
+
'lib/index_manager.rb'
|
348
|
+
end
|
349
|
+
|
350
|
+
# TODO: get 'https://raw.github.com/...', '...'
|
351
|
+
|
352
|
+
git add: "."
|
353
|
+
git commit: "-m 'Added the IndexManager class'"
|
354
|
+
|
355
|
+
# ----- Import the data ---------------------------------------------------------------------------
|
356
|
+
|
357
|
+
puts
|
358
|
+
say_status "Data", "Import the data...", :yellow
|
359
|
+
puts '-'*80, ''; sleep 0.25
|
360
|
+
|
361
|
+
source = ENV.fetch('DATA_SOURCE', 'http://ruby-demo-assets.s3.amazonaws.com/dischord.yml')
|
362
|
+
|
363
|
+
run "rails runner 'IndexManager.import_from_yaml(\"#{source}\", force: true)'"
|
364
|
+
|
365
|
+
# ----- Print Git log -----------------------------------------------------------------------------
|
366
|
+
|
367
|
+
puts
|
368
|
+
say_status "Git", "Details about the application:", :yellow
|
369
|
+
puts '-'*80, ''
|
370
|
+
|
371
|
+
run "git --no-pager log --reverse --oneline"
|
372
|
+
|
373
|
+
# ----- Start the application ---------------------------------------------------------------------
|
374
|
+
|
375
|
+
unless ENV['RAILS_NO_SERVER_START']
|
376
|
+
require 'net/http'
|
377
|
+
if (begin; Net::HTTP.get(URI('http://localhost:3000')); rescue Errno::ECONNREFUSED; false; rescue Exception; true; end)
|
378
|
+
puts "\n"
|
379
|
+
say_status "ERROR", "Some other application is running on port 3000!\n", :red
|
380
|
+
puts '-'*80
|
381
|
+
|
382
|
+
port = ask("Please provide free port:", :bold)
|
383
|
+
else
|
384
|
+
port = '3000'
|
385
|
+
end
|
386
|
+
|
387
|
+
puts "", "="*80
|
388
|
+
say_status "DONE", "\e[1mStarting the application.\e[0m", :yellow
|
389
|
+
puts "="*80, ""
|
390
|
+
|
391
|
+
run "rails server --port=#{port}"
|
392
|
+
end
|