interpret 0.1.1

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.
Files changed (88) hide show
  1. data/.gitignore +11 -0
  2. data/Gemfile +4 -0
  3. data/Rakefile +2 -0
  4. data/app/controllers/interpret/base_controller.rb +10 -0
  5. data/app/controllers/interpret/search_controller.rb +7 -0
  6. data/app/controllers/interpret/tools_controller.rb +39 -0
  7. data/app/controllers/interpret/translations_controller.rb +47 -0
  8. data/app/models/interpret/translation.rb +257 -0
  9. data/app/sweepers/interpret/base_sweeper.rb +14 -0
  10. data/app/sweepers/interpret/translation_sweeper.rb +14 -0
  11. data/app/views/interpret/search/index.html.erb +29 -0
  12. data/app/views/interpret/search/perform.html.erb +38 -0
  13. data/app/views/interpret/tools/index.html.erb +38 -0
  14. data/app/views/interpret/translations/_form.html.erb +5 -0
  15. data/app/views/interpret/translations/_listing.html.erb +22 -0
  16. data/app/views/interpret/translations/edit.html.erb +5 -0
  17. data/app/views/interpret/translations/index.html.erb +28 -0
  18. data/app/views/layouts/interpret.html.erb +41 -0
  19. data/config/routes.rb +20 -0
  20. data/interpret.gemspec +30 -0
  21. data/lib/generators/interpret/migration_generator.rb +25 -0
  22. data/lib/generators/interpret/setup_generator.rb +21 -0
  23. data/lib/generators/interpret/templates/migration.rb +16 -0
  24. data/lib/generators/interpret/views_generator.rb +16 -0
  25. data/lib/interpret/capistrano.rb +15 -0
  26. data/lib/interpret/engine.rb +23 -0
  27. data/lib/interpret/helpers.rb +45 -0
  28. data/lib/interpret/lazy_hash.rb +21 -0
  29. data/lib/interpret/logger.rb +7 -0
  30. data/lib/interpret/version.rb +3 -0
  31. data/lib/interpret.rb +30 -0
  32. data/lib/tasks/interpret.rake +11 -0
  33. data/public/javascripts/jquery.purr.js +180 -0
  34. data/public/stylesheets/folder.png +0 -0
  35. data/public/stylesheets/interpret_style.css +542 -0
  36. data/test_app/Gemfile +11 -0
  37. data/test_app/README +256 -0
  38. data/test_app/Rakefile +7 -0
  39. data/test_app/app/controllers/application_controller.rb +3 -0
  40. data/test_app/app/controllers/pages_controller.rb +3 -0
  41. data/test_app/app/helpers/application_helper.rb +2 -0
  42. data/test_app/app/sweepers/page_sweeper.rb +12 -0
  43. data/test_app/app/views/layouts/application.html.erb +15 -0
  44. data/test_app/app/views/pages/contact.html.haml +8 -0
  45. data/test_app/app/views/pages/index.html.haml +9 -0
  46. data/test_app/config/application.rb +42 -0
  47. data/test_app/config/boot.rb +13 -0
  48. data/test_app/config/database.yml +23 -0
  49. data/test_app/config/environment.rb +5 -0
  50. data/test_app/config/environments/development.rb +27 -0
  51. data/test_app/config/environments/production.rb +51 -0
  52. data/test_app/config/environments/test.rb +35 -0
  53. data/test_app/config/initializers/backtrace_silencers.rb +7 -0
  54. data/test_app/config/initializers/inflections.rb +10 -0
  55. data/test_app/config/initializers/interpret.rb +2 -0
  56. data/test_app/config/initializers/mime_types.rb +5 -0
  57. data/test_app/config/initializers/secret_token.rb +7 -0
  58. data/test_app/config/initializers/session_store.rb +8 -0
  59. data/test_app/config/locales/ca.yml +6 -0
  60. data/test_app/config/locales/es.yml +48 -0
  61. data/test_app/config/routes.rb +4 -0
  62. data/test_app/config.ru +4 -0
  63. data/test_app/db/migrate/20110209185258_interpret_create_translations.rb +16 -0
  64. data/test_app/db/schema.rb +23 -0
  65. data/test_app/db/seeds.rb +0 -0
  66. data/test_app/lib/lazy_hash.rb +22 -0
  67. data/test_app/lib/tasks/.gitkeep +0 -0
  68. data/test_app/lib/tasks/setup.rake +19 -0
  69. data/test_app/public/404.html +26 -0
  70. data/test_app/public/422.html +26 -0
  71. data/test_app/public/500.html +26 -0
  72. data/test_app/public/favicon.ico +0 -0
  73. data/test_app/public/index.html +29 -0
  74. data/test_app/public/javascripts/application.js +2 -0
  75. data/test_app/public/javascripts/best_in_place.js +456 -0
  76. data/test_app/public/javascripts/controls.js +965 -0
  77. data/test_app/public/javascripts/dragdrop.js +974 -0
  78. data/test_app/public/javascripts/effects.js +1123 -0
  79. data/test_app/public/javascripts/jquery.purr.js +180 -0
  80. data/test_app/public/javascripts/prototype.js +6001 -0
  81. data/test_app/public/javascripts/rails.js +134 -0
  82. data/test_app/public/robots.txt +5 -0
  83. data/test_app/public/stylesheets/.gitkeep +0 -0
  84. data/test_app/public/stylesheets/folder.png +0 -0
  85. data/test_app/public/stylesheets/interpret_style.css +530 -0
  86. data/test_app/script/rails +6 -0
  87. data/test_app/vendor/plugins/.gitkeep +0 -0
  88. metadata +262 -0
data/.gitignore ADDED
@@ -0,0 +1,11 @@
1
+ pkg/*
2
+ *.gem
3
+ .bundle
4
+
5
+ Gemfile.lock
6
+ .DS_Store
7
+ test_app/.bundle
8
+ test_app/db/*.sqlite3
9
+ test_app/log/*.log
10
+ test_app/tmp/**/*
11
+
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in interpret.gemspec
4
+ gemspec
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require 'bundler'
2
+ Bundler::GemHelper.install_tasks
@@ -0,0 +1,10 @@
1
+ class Interpret::BaseController < eval(Interpret.controller.classify)
2
+ before_filter :set_locale
3
+ layout 'interpret'
4
+
5
+ private
6
+ def set_locale
7
+ I18n.locale = params[:locale] if params[:locale]
8
+ end
9
+ end
10
+
@@ -0,0 +1,7 @@
1
+ class Interpret::SearchController < Interpret::BaseController
2
+
3
+ def perform
4
+ t = Interpret::Translation.arel_table
5
+ @translations = Interpret::Translation.locale(I18n.locale).where(t[:key].matches("%#{params[:key]}%").and(t[:value].matches("%#{params[:value]}%")) )
6
+ end
7
+ end
@@ -0,0 +1,39 @@
1
+ class Interpret::ToolsController < Interpret::BaseController
2
+
3
+ def dump
4
+ Interpret::Translation.dump
5
+
6
+ session.delete(:tree)
7
+ Interpret.backend.reload! if Interpret.backend
8
+ redirect_to interpret_tools_url, :notice => "Dump done."
9
+ end
10
+
11
+ def export
12
+ require 'ya2yaml'
13
+
14
+ translations = Interpret::Translation.locale(I18n.locale).all
15
+ hash = Interpret::Translation.export(translations)
16
+ text = hash.ya2yaml
17
+
18
+ send_data text[5..text.length], :filename => "#{I18n.locale}.yml"
19
+ end
20
+
21
+ def import
22
+ unless params.has_key? :file
23
+ redirect_to interpret_tools_url, :alert => "You have to select a file to import."
24
+ return
25
+ end
26
+
27
+ begin
28
+ Interpret::Translation.import(params[:file])
29
+ rescue Exception => e
30
+ redirect_to interpret_tools_url, :alert => e
31
+ end
32
+
33
+ session.delete(:tree)
34
+ Interpret.backend.reload! if Interpret.backend
35
+
36
+ redirect_to interpret_tools_url, :notice => "Import successfully done."
37
+ end
38
+ end
39
+
@@ -0,0 +1,47 @@
1
+ class Interpret::TranslationsController < Interpret::BaseController
2
+ cache_sweeper eval(Interpret.sweeper.to_s.classify) if Interpret.sweeper
3
+ cache_sweeper Interpret::TranslationSweeper
4
+ before_filter :get_tree, :only => :index
5
+
6
+ def index
7
+ key = params[:key]
8
+ t = Interpret::Translation.arel_table
9
+ if key
10
+ @translations = Interpret::Translation.locale(I18n.locale).where(t[:key].matches("#{key}.%"))
11
+ @translations = @translations.select{|x| x.key =~ /#{key}\.\w+$/}
12
+ else
13
+ @translations = Interpret::Translation.locale(I18n.locale).where(t[:key].does_not_match("%.%")).paginate :page => params[:page]
14
+ end
15
+ end
16
+
17
+ def edit
18
+ @translation = Interpret::Translation.find(params[:id])
19
+ end
20
+
21
+ def update
22
+ @translation = Interpret::Translation.find(params[:id])
23
+ old_value = @translation.value
24
+
25
+ respond_to do |format|
26
+ if @translation.update_attributes(params[:interpret_translation])
27
+ msg = respond_to?(:current_user) ? "By [#{current_user}]. " : ""
28
+ msg << "Locale: [#{@translation.locale}], key: [#{@translation.key}]. The translation has been changed from [#{old_value}] to [#{@translation.value}]"
29
+ Interpret.logger.info msg
30
+
31
+ format.html { redirect_to(translations_url)}
32
+ format.xml { head :ok }
33
+ format.json { head :ok }
34
+ else
35
+ format.html { render :action => "edit" }
36
+ format.xml { render :xml => @translation.errors, :status => :unprocessable_entity }
37
+ format.json { render :status => :unprocessable_entity }
38
+ end
39
+ end
40
+ end
41
+
42
+ private
43
+ def get_tree
44
+ @tree = session[:tree] ||= Interpret::Translation.get_tree
45
+ end
46
+
47
+ end
@@ -0,0 +1,257 @@
1
+ require 'i18n/backend/active_record/translation'
2
+
3
+
4
+ module Interpret
5
+
6
+ class TableDoesNotExists < ActiveRecord::ActiveRecordError; end
7
+
8
+ unless I18n::Backend::ActiveRecord::Translation.table_exists?
9
+ raise TableDoesNotExists, "You must setup a translations table first"
10
+ end
11
+
12
+ class Translation < I18n::Backend::ActiveRecord::Translation
13
+ default_scope order('locale ASC')
14
+
15
+ class << self
16
+ # Generates a hash representing the tree structure of the translations
17
+ # for the given locale. It includes only "folders" in the sense of
18
+ # locale keys that includes some real translations, or other keys.
19
+ def get_tree(lang = I18n.locale)
20
+ t = arel_table
21
+ all_trans = locale(lang).select(t[:key]).where(t[:key].matches("%.%")).all
22
+
23
+ tree = LazyHash.build_hash
24
+ all_trans = all_trans.map{|x| x.key.split(".")[0..-2].join(".")}.uniq
25
+ all_trans.each do |x|
26
+ LazyHash.lazy_add(tree, x, {})
27
+ end
28
+
29
+ # Generate a new clean hash without the proc's from LazyHash.
30
+ # Includes a root level for convenience, to be exactly like the
31
+ # structure of a .yml file which has the "en" root key for example.
32
+ {"index" => eval(tree.inspect)}
33
+ end
34
+
35
+ # Generate a hash from the given translations. That hash can be
36
+ # ya2yaml'ized to get a standard .yml locale file.
37
+ def export(translations)
38
+ res = LazyHash.build_hash
39
+
40
+ translations.each do |e|
41
+ LazyHash.lazy_add(res, "#{e.locale}.#{e.key}", e.value)
42
+ end
43
+ res
44
+ end
45
+
46
+ # Import the contents of the given .yml locale file into the database
47
+ # backend. All the existing translations for the given language will be
48
+ # erased, the backend will contain only the translations from the file
49
+ # (in that language).
50
+ #
51
+ # The language will be obtained from the first unique key of the yml
52
+ # file.
53
+ def import(file)
54
+ if file.content_type && file.content_type.match(/^text\/.*/).nil?
55
+ raise ArgumentError, "Invalid file content type"
56
+ end
57
+ hash = YAML.load file
58
+ raise ArgumentError, "the YAML file must contain an unique first key representing the locale" unless hash.keys.count == 1
59
+
60
+ lang = hash.keys.first
61
+ to_remove = locale(lang).all
62
+ to_remove.each do |x|
63
+ x.destroy
64
+ end
65
+ records = parse_hash(hash.first[1], lang)
66
+ # TODO: Replace with activerecord-import bulk inserts
67
+ transaction do
68
+ records.each {|x| x.save!}
69
+ end
70
+ end
71
+
72
+ # Dump all contents from *.yml locale files into the database.
73
+ # CAUTION: All existing data will be erased!
74
+ #
75
+ # It will create a "#{locale}.yml.backup" file into config/locales
76
+ # for each language present in the database, in case you want to
77
+ # recover some of your just-erased translations.
78
+ # If you don't want backups, set:
79
+ #
80
+ # Interpret.options[:dump_without_backup] = true
81
+ def dump
82
+ files = Dir[Rails.root.join("config", "locales", "*.yml").to_s]
83
+ delete_all
84
+
85
+ records = []
86
+ files.each do |f|
87
+ ar = YAML.load_file f
88
+ locale = ar.keys.first
89
+ records += parse_hash(ar.first[1], locale)
90
+ end
91
+
92
+ # TODO: Replace with activerecord-import bulk inserts
93
+ transaction do
94
+ records.each {|x| x.save!}
95
+ end
96
+ end
97
+
98
+ # Run a smart update from the translations in .yml files into the
99
+ # databse backend. It issues a merging from both, comparing each key
100
+ # present in the db with the one from the yml file.
101
+ #
102
+ # The use case beyond this arquitecture presuposes some things:
103
+ #
104
+ # 1) You're working in development mode with the default I18n backend,
105
+ # that is with the translations in the config/locales/*.yml files.
106
+ #
107
+ # 2) Your application is deployed in production and running well. Also,
108
+ # it has support to modify it's contents (from this very gem of course)
109
+ # on live, so its possible that your customer has changed a sentence or
110
+ # a title of the site. And you want to preserve that.
111
+ #
112
+ # 3) In general, from the very moment you choose to give the users (or
113
+ # admins) of your site the ability to change the contents, that contents
114
+ # are no longer part of the "project" (are checked in in git, to be
115
+ # specific), they are now part of the dynamic contents of the site just
116
+ # as if they were models in your db.
117
+ #
118
+ # In development, you define a "content layout" in the sense of a
119
+ # specific locale keys hierarchy. How many paragraphs are in your views,
120
+ # how many titles, etc... But the real paragraphs are in the production
121
+ # database.
122
+ #
123
+ # So, with this "update" action, you are updating that "contents layout"
124
+ # with the new one you just designed in development.
125
+ #
126
+ # Also keep in mind that rails let you have a diferent locale key
127
+ # hierarchy for each language, and this behaviour is prohibited in
128
+ # interpret.
129
+ # Here, the I18n.default_locale configured in your app is considered the
130
+ # main one, that is, the only language that can be trusted to have all
131
+ # the required and correct locale keys.
132
+ # This will be used to check for inconsitent translations into other
133
+ # languages, knowing what you haven't translated yet.
134
+ #
135
+ # What does all that means?
136
+ #
137
+ # - First of all, get the locale keys for the main language from yml files.
138
+ # - For all of these locale keys, do:
139
+ # - If a key is present in the db, but not in the new ones, remove
140
+ # it. You have removed it from the new content layout, so it's no longer
141
+ # needed.
142
+ # - If the key is not present in the db, it's new. So, create a new
143
+ # entry for that key in each language. Look if a translation for that
144
+ # key exists in yml files for each language, if it exists, use it. If
145
+ # not, left it empty.
146
+ # - If the key already exists in the db, do nothing. Maybe somone has
147
+ # changed that content in production, and you don't want to lose
148
+ # that. Or maybe you do want to change that content, because you
149
+ # just added the correct sentence in the yml files. It's up to you to
150
+ # do the right thing.
151
+ def update
152
+ files = Dir[Rails.root.join("config", "locales", "*.yml").to_s]
153
+
154
+ @languages = {}
155
+ @main = {}
156
+ files.each do |f|
157
+ ar = YAML.load_file f
158
+ lang = ar.keys.first
159
+ @languages[lang.to_s] = ar.first[1]
160
+ if I18n.default_locale.to_s == lang.to_s
161
+ @main = ar.first[1]
162
+ @main_lang = lang
163
+ end
164
+ end
165
+
166
+ sync(@main)
167
+ end
168
+
169
+ private
170
+ def sync(hash, prefix = "", existing = nil)
171
+ if existing.nil?
172
+ translations = locale(@main_lang).all
173
+ existing = export(translations)
174
+ existing = existing.first[1] unless existing.empty?
175
+ end
176
+
177
+ hash.keys.each do |x|
178
+ existing.delete(x)
179
+
180
+ if hash[x].kind_of?(Hash)
181
+ sync(hash[x], "#{prefix}#{x}.", existing[x])
182
+ else
183
+ old = locale(@main_lang).find_by_key("#{prefix}#{x}")
184
+
185
+ unless old
186
+ # Creates the new entry
187
+ create_new_translation("#{prefix}#{x}")
188
+ else
189
+ # Check if the entry exists in the other languages
190
+ check_in_other_langs("#{prefix}#{x}")
191
+ end
192
+ end
193
+ end
194
+
195
+ if prefix.blank?
196
+ remove_unused_keys(existing)
197
+ end
198
+ end
199
+
200
+ # Check if the the given key exists in all languages except @main. If
201
+ # not, create an entry.
202
+ def check_in_other_langs(key)
203
+ (@languages.keys - [@main_lang]).each do |lang|
204
+ trans = locale(lang).find_by_key(key)
205
+ if trans.nil?
206
+ create! :locale => lang,
207
+ :key => key,
208
+ :value => ""
209
+ Interpret.logger.info "Created inexistent key [#{key}] for lang [#{lang}]"
210
+ end
211
+ end
212
+ end
213
+
214
+ def create_new_translation(key)
215
+ @languages.keys.each do |lang|
216
+ origin_hash = @languages[lang].clone
217
+ key.split(".")[0..-2].each do |key|
218
+ origin_hash = origin_hash[key]
219
+ end
220
+ value = origin_hash[key.split(".").last]
221
+ create! :locale => lang,
222
+ :key => key,
223
+ :value => value
224
+ end
225
+ Interpret.logger.info "New key created [#{key}] for languages #{@languages.keys.inspect}"
226
+ end
227
+
228
+ def remove_unused_keys(hash, prefix = "")
229
+ hash.keys.each do |x|
230
+ if hash[x].kind_of?(Hash)
231
+ remove_unused_keys(hash[x], "#{prefix}#{x}.")
232
+ else
233
+ delete_all(:locale => @languages.keys, :key => "#{prefix}#{x}")
234
+ Interpret.logger.info "Removing unused key #{prefix}#{x}"
235
+ end
236
+ end
237
+ end
238
+
239
+ def parse_hash(dict, locale, prefix = "")
240
+ res = []
241
+ dict.keys.each do |x|
242
+ if dict[x].kind_of?(Hash)
243
+ res += parse_hash(dict[x], locale, "#{prefix}#{x}.")
244
+ else
245
+ res << new(:locale => locale,
246
+ :key => "#{prefix}#{x}",
247
+ :value => dict[x])
248
+ end
249
+ end
250
+ res
251
+ end
252
+
253
+
254
+ end
255
+ end
256
+ end
257
+
@@ -0,0 +1,14 @@
1
+ class Interpret::BaseSweeper < ActionController::Caching::Sweeper
2
+ observe Interpret::Translation
3
+
4
+ def after_update(translation)
5
+ expire_cache(translation)
6
+ end
7
+
8
+ protected
9
+
10
+ # Implement user's custom expire logic
11
+ def expire_cache(translation)
12
+ end
13
+ end
14
+
@@ -0,0 +1,14 @@
1
+ class Interpret::TranslationSweeper < ActionController::Caching::Sweeper
2
+ observe Interpret::Translation
3
+
4
+ def after_update(translation)
5
+ Interpret.backend.reload! if Interpret.backend
6
+ end
7
+
8
+ private
9
+ def expire_cache
10
+ #expire_action :controller => "interpret/translations", :action => :tree
11
+ session.delete(:tree)
12
+ Interpret.backend.reload! if Interpret.backend
13
+ end
14
+ end
@@ -0,0 +1,29 @@
1
+ <div id="header">
2
+ <h1>Search translations</h1>
3
+ </div>
4
+
5
+ <div id="search">
6
+ <p>Enter a search term for the key and/or the value of the translation</p>
7
+
8
+ <%= form_tag interpret_search_for_path do %>
9
+ <%= label_tag "key", "Key value" %>
10
+ <br />
11
+ <%= text_field_tag "key" %>
12
+ <br />
13
+
14
+ <%= label_tag "value", "Translation text" %>
15
+ <br />
16
+ <%= text_field_tag "value" %>
17
+ <br />
18
+
19
+ <%= submit_tag "SEARCH" %>
20
+
21
+ <% end %>
22
+
23
+ <%= content_for :sidebar do %>
24
+ <h2>Search</h2>
25
+ <p>
26
+ You can use this search feature to look into all the translations. Can be filtered by language, key and phrase.
27
+ </p>
28
+ <% end %>
29
+ </div>
@@ -0,0 +1,38 @@
1
+ <%= content_for :title do %>
2
+ Search translations
3
+ <%= "by " unless params[:key].blank? && params[:value].blank? %>
4
+ <%= params[:key] unless params[:key].blank? %>
5
+ <%= "and " unless params[:key].blank? || params[:value].blank? %>
6
+ <%= params[:value] unless params[:value].blank? %>
7
+ <% end %>
8
+
9
+ <div id="header">
10
+ <h1>Search translations</h1>
11
+ </div>
12
+
13
+
14
+ <%= render 'interpret/translations/listing' %>
15
+
16
+
17
+ <%= content_for :sidebar do %>
18
+ <h2>Search</h2>
19
+ <p>
20
+ <%= @translations.size %> results found.
21
+ </p>
22
+ <div id="side_search">
23
+ <%= form_tag interpret_search_for_path do %>
24
+ <%= label_tag "key", "Key value" %>
25
+ <br />
26
+ <%= text_field_tag "key", params[:key] %>
27
+ <br />
28
+
29
+ <%= label_tag "value", "Translation text" %>
30
+ <br />
31
+ <%= text_field_tag "value", params[:value] %>
32
+ <br />
33
+
34
+ <%= submit_tag "SEARCH" %>
35
+
36
+ <% end %>
37
+ </div>
38
+ <% end %>
@@ -0,0 +1,38 @@
1
+ <div class="header">
2
+ <h1>Your master language</h1>
3
+ </div>
4
+ <p>
5
+ Currently your primary language is <b><%= I18n.default_locale %></b>. This
6
+ language will be used as a reference for all your translation work, you
7
+ can change it below:
8
+ </p>
9
+ <p><em>TODO</em></p>
10
+
11
+ <div class="header">
12
+ <h1>Dump .yml contents into database</h1>
13
+ </div>
14
+
15
+ <p>With this option you can export all of your *.yml contents into the database backend<br/>
16
+ <b>Be aware!!</b> All of your current database translations will be erased
17
+ </p>
18
+
19
+ <% if Rails.env == "production" %>
20
+ <p><b>MY GOD!!! You're in PRODUCTION!! You're sure you wanna do this??</b></p>
21
+ <% end %>
22
+
23
+ <p>
24
+ <%= button_to "Run the migration", dump_interpret_tools_path %>
25
+ </p>
26
+
27
+ <div class="header">
28
+ <h1>Tools for import/export locale data</h1>
29
+ </div>
30
+
31
+ <p><%= link_to "Download", export_interpret_tools_path %> the current translations for '<%= I18n.locale %>' language as .yml file</p>
32
+ <p>Upload your .yml file for '<%= I18n.locale %>' language</p>
33
+ <p>
34
+ <%= form_tag import_interpret_tools_path, :multipart => true do %>
35
+ <%= label_tag "File:" %>
36
+ <%= file_field_tag :file %>
37
+ <%= submit_tag "Upload" %>
38
+ <% end %>
@@ -0,0 +1,5 @@
1
+ <%= form_for @translation, :url => translation_path(@translation) do |f| %>
2
+ <%= f.label :value %>
3
+ <%= f.text_field :value, :value => @translation.value %>
4
+ <%= f.submit %>
5
+ <% end %>
@@ -0,0 +1,22 @@
1
+ <table>
2
+ <thead>
3
+ <tr class="header">
4
+ <th>Key</th>
5
+ <th>Content</th>
6
+ </tr>
7
+ </thead>
8
+ <tbody>
9
+ <% @translations.each do |x| %>
10
+ <tr id="translation_<%= x.id %>">
11
+ <td><%= x.key %></td>
12
+ <td>
13
+ <%= best_in_place x, :value,
14
+ :type => :textarea,
15
+ :path => interpret_translation_path(x),
16
+ :activator => "#translation_#{x.id}",
17
+ :sanitize => false %>
18
+ </td>
19
+ </tr>
20
+ <% end %>
21
+ </tbody>
22
+ </table>
@@ -0,0 +1,5 @@
1
+ <h1>[<%= I18n.locale %>] Editing '<%= @translation.key %>'</h1>
2
+
3
+ <%= render 'form' %>
4
+
5
+ <%= link_to "Back", translations_path %>
@@ -0,0 +1,28 @@
1
+ <%= content_for :title do %>
2
+ Translation list
3
+ <% end %>
4
+ <div id="header">
5
+ <h1>Translations for <%= I18n.locale %></h1>
6
+ </div>
7
+ <p>
8
+ Below are the translations without any particulary key in your application.
9
+ That use to be some global names or terms for common use along all the site,
10
+ which doesn't belong to any page or section in particulary. To dive into the
11
+ rest of your app's contents, navigate using the tree in the left, that shows your
12
+ locales structure.
13
+ </p>
14
+
15
+ <%= render 'interpret/translations/listing' %>
16
+
17
+ <%= content_for :sidebar do %>
18
+ <div id="tree_sidebar">
19
+ <h3>
20
+ <% if params[:key] %>
21
+ /<%= params[:key].split(".").join("/") %>
22
+ <% else %>
23
+ /
24
+ <% end %>
25
+ </h3>
26
+ <%= show_interpret_tree(@tree, params[:key]) %>
27
+ </div>
28
+ <% end %>
@@ -0,0 +1,41 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>INTERPRET - <%= yield :title %></title>
5
+ <%= stylesheet_link_tag "interpret_style" %>
6
+ <%= javascript_include_tag "https://ajax.googleapis.com/ajax/libs/jquery/1.4.4/jquery.min.js" %>
7
+ <%= javascript_include_tag "jquery.purr" %>
8
+ <%= javascript_include_tag "best_in_place" %>
9
+ <%= csrf_meta_tag %>
10
+ </head>
11
+ <body>
12
+ <div id="container">
13
+ <div class="menu grid_16">
14
+ <%= interpret_section_link_to "Overview", interpret_root_path %> |
15
+ <%= interpret_section_link_to "Tools", interpret_tools_path %> |
16
+ <%= interpret_section_link_to "Search", interpret_search_path %>
17
+ <hr />
18
+ </div>
19
+ <div class="menu grid_16">
20
+ Languages:
21
+ <% I18n.available_locales.each do |locale| %>
22
+ <%= link_to locale, :locale => locale %>
23
+ <% end %>
24
+ <hr />
25
+ </div>
26
+ <div id="sidebar" class="grid_3">
27
+ <%= yield :sidebar %>
28
+ </div>
29
+ <div id="main" class="grid_13">
30
+ <%= yield %>
31
+ </div>
32
+ </div>
33
+
34
+ <%= javascript_tag do %>
35
+ $(document).ready(function() {
36
+ /* Activating Best In Place */
37
+ jQuery(".best_in_place").best_in_place()
38
+ });
39
+ <% end %>
40
+ </body>
41
+ </html>
data/config/routes.rb ADDED
@@ -0,0 +1,20 @@
1
+ Rails.application.routes.draw do
2
+ scope Interpret.scope do
3
+ namespace :interpret do
4
+ resources :translations, :only => [:edit, :update]
5
+
6
+ resources :tools, :only => :index do
7
+ collection do
8
+ get :export
9
+ post :import
10
+ post :dump
11
+ end
12
+ end
13
+
14
+ match "search", :to => "search#index"
15
+ match "search_for", :to => "search#perform"
16
+
17
+ root :to => "translations#index"
18
+ end
19
+ end
20
+ end