spina 2.2.0 → 2.3.3
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of spina might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/app/assets/config/spina/manifest.js +1 -0
- data/app/assets/javascripts/spina/application.js +2 -0
- data/app/assets/javascripts/spina/controllers/attachment_picker_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/autofocus_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/button_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/confetti_controller.js +2 -2
- data/app/assets/javascripts/spina/controllers/confirm_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/delegate_click_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/exists_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/form_controller.js +2 -2
- data/app/assets/javascripts/spina/controllers/hotkeys_controller.js +2 -2
- data/app/assets/javascripts/spina/controllers/image_collection_controller.js +2 -2
- data/app/assets/javascripts/spina/controllers/image_fade_in_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/infinite_scroll_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/loading_button_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/media_picker_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/media_picker_modal_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/modal_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/navigation_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/parent_pages_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/repeater_controller.js +2 -2
- data/app/assets/javascripts/spina/controllers/select_placeholder_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/selectable_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/shortcuts_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/sortable_controller.js +3 -3
- data/app/assets/javascripts/spina/controllers/switch_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/tabs_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/toggle_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/trix_controller.js +1 -1
- data/app/assets/javascripts/spina/controllers/unique_id_controller.js +1 -1
- data/app/assets/javascripts/spina/libraries/stimulus-reveal@1.2.4.js +1 -1
- data/app/assets/stylesheets/spina/_tailwind.css +110078 -105581
- data/app/components/spina/media_picker/modal_component.html.erb +2 -2
- data/app/controllers/concerns/spina/api/paginable.rb +44 -0
- data/app/controllers/spina/api/api_controller.rb +29 -0
- data/app/controllers/spina/api/images_controller.rb +12 -0
- data/app/controllers/spina/api/navigations_controller.rb +20 -0
- data/app/controllers/spina/api/pages_controller.rb +26 -0
- data/app/controllers/spina/api/resources_controller.rb +19 -0
- data/app/helpers/spina/images_helper.rb +1 -5
- data/app/helpers/spina/spina_helper.rb +5 -8
- data/app/models/spina/page.rb +1 -1
- data/app/serializers/spina/api/base_serializer.rb +6 -0
- data/app/serializers/spina/api/image_serializer.rb +20 -0
- data/app/serializers/spina/api/navigation_serializer.rb +30 -0
- data/app/serializers/spina/api/page_serializer.rb +28 -0
- data/app/serializers/spina/api/resource_serializer.rb +12 -0
- data/app/views/layouts/spina/admin/application.html.erb +3 -7
- data/app/views/spina/admin/shared/_navigation.html.erb +2 -2
- data/config/locales/ru.yml +199 -177
- data/config/routes.rb +10 -0
- data/lib/generators/spina/templates/config/initializers/spina.rb +12 -0
- data/lib/spina.rb +11 -2
- data/lib/spina/engine.rb +12 -4
- data/lib/spina/railtie.rb +1 -1
- data/lib/spina/version.rb +1 -1
- data/lib/tasks/spina_tasks.rake +1 -1
- metadata +51 -13
- data/app/assets/javascripts/spina/importmap.json.erb +0 -5
- data/lib/spina/importmap_helper.rb +0 -37
@@ -25,7 +25,7 @@
|
|
25
25
|
</div>
|
26
26
|
|
27
27
|
<div class="md:w-72 p-4 border-t rounded-b-lg md:rounded-none md:border-t-0 border-gray-200 flex flex-col justify-between bg-gray-100 md:bg-opacity-50 md:rounded-l-lg">
|
28
|
-
<div class="hidden md:block md:mb-6">
|
28
|
+
<div class="hidden md:block md:mb-6 overflow-scroll">
|
29
29
|
<%= link_to helpers.spina.admin_media_picker_path, class: "font-medium w-full text-sm px-3 py-2 rounded-lg flex items-center justify-between #{media_folder_classes(nil)}", data: {turbo_frame: "media_picker"} do %>
|
30
30
|
<div class="flex items-center">
|
31
31
|
<%= helpers.heroicon("collection", style: :solid, class: "w-5 h-5 mr-2 text-spina-light") %>
|
@@ -36,7 +36,7 @@
|
|
36
36
|
<%= image_count %>
|
37
37
|
</div>
|
38
38
|
<% end %>
|
39
|
-
|
39
|
+
|
40
40
|
<% media_folders.each do |media_folder| %>
|
41
41
|
<%= link_to helpers.spina.admin_media_picker_path(media_folder_id: media_folder.id), class: "font-medium w-full text-gray-600 text-sm px-3 py-2 cursor-pointer rounded-lg flex items-center justify-between #{media_folder_classes(media_folder)}", data: {turbo_frame: "media_picker"} do %>
|
42
42
|
<div class="flex items-center">
|
@@ -0,0 +1,44 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
module Paginable
|
4
|
+
extend ActiveSupport::Concern
|
5
|
+
|
6
|
+
private
|
7
|
+
|
8
|
+
def pagination(records)
|
9
|
+
paginated_records = records.page(params[:page]).per(params[:per_page])
|
10
|
+
[paginated_records, {
|
11
|
+
meta: pagination_meta(paginated_records),
|
12
|
+
links: pagination_links(paginated_records)
|
13
|
+
}]
|
14
|
+
end
|
15
|
+
|
16
|
+
def pagination_meta(paginated_records)
|
17
|
+
{
|
18
|
+
current_page: paginated_records.current_page,
|
19
|
+
total: paginated_records.total_count,
|
20
|
+
per_page: paginated_records.limit_value,
|
21
|
+
path: view_context.url_for(only_path: true)
|
22
|
+
}
|
23
|
+
end
|
24
|
+
|
25
|
+
def pagination_links(paginated_records)
|
26
|
+
{
|
27
|
+
first: path_to_first_page,
|
28
|
+
prev: view_context.path_to_prev_page(paginated_records),
|
29
|
+
next: view_context.path_to_next_page(paginated_records),
|
30
|
+
last: path_to_last_page(paginated_records)
|
31
|
+
}
|
32
|
+
end
|
33
|
+
|
34
|
+
def path_to_first_page
|
35
|
+
view_context.url_for(page: 1, per_page: params[:per_page], only_path: true)
|
36
|
+
end
|
37
|
+
|
38
|
+
def path_to_last_page(paginated_records)
|
39
|
+
view_context.url_for(page: paginated_records.total_pages, per_page: params[:per_page], only_path: true)
|
40
|
+
end
|
41
|
+
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
class ApiController < ActionController::Base
|
4
|
+
include Spina::CurrentAccount, Spina::CurrentTheme
|
5
|
+
|
6
|
+
protect_from_forgery unless: -> { request.format.json? }
|
7
|
+
|
8
|
+
rescue_from ActiveRecord::RecordNotFound, with: :render_404
|
9
|
+
|
10
|
+
TOKEN = Spina.config.api_key
|
11
|
+
|
12
|
+
before_action :authenticate_api
|
13
|
+
|
14
|
+
private
|
15
|
+
|
16
|
+
def render_404
|
17
|
+
render json: {error: "Not Found"}, status: :not_found
|
18
|
+
end
|
19
|
+
|
20
|
+
def authenticate_api
|
21
|
+
head :not_found and return if TOKEN.blank?
|
22
|
+
authenticate_or_request_with_http_token do |token, options|
|
23
|
+
ActiveSupport::SecurityUtils.secure_compare(token, TOKEN)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
class ImagesController < ApiController
|
4
|
+
|
5
|
+
def show
|
6
|
+
@image = Spina::Image.find(params[:id])
|
7
|
+
render json: Spina::Api::ImageSerializer.new(@image, {params: {view_context: view_context}}).serializable_hash.to_json
|
8
|
+
end
|
9
|
+
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
class NavigationsController < ApiController
|
4
|
+
include Paginable
|
5
|
+
|
6
|
+
def index
|
7
|
+
navigations = Navigation.order(:id)
|
8
|
+
paginated = pagination(navigations)
|
9
|
+
render json: Spina::Api::NavigationSerializer.new(paginated.first, paginated.last.merge(fields: {navigation: [:name, :label]})).serializable_hash.to_json
|
10
|
+
end
|
11
|
+
|
12
|
+
def show
|
13
|
+
@navigation = Navigation.find(params[:id])
|
14
|
+
render json: Spina::Api::NavigationSerializer.new(@navigation).serializable_hash.to_json
|
15
|
+
end
|
16
|
+
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
class PagesController < ApiController
|
4
|
+
include Paginable
|
5
|
+
|
6
|
+
before_action :set_resource
|
7
|
+
|
8
|
+
def index
|
9
|
+
pages = Page.live.includes(:translations).where(resource: @resource).order(:created_at)
|
10
|
+
render json: Spina::Api::PageSerializer.new(*pagination(pages)).serializable_hash.to_json
|
11
|
+
end
|
12
|
+
|
13
|
+
def show
|
14
|
+
@page = Page.live.where(resource: @resource).find(params[:id])
|
15
|
+
render json: Spina::Api::PageSerializer.new(@page).serializable_hash.to_json
|
16
|
+
end
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
def set_resource
|
21
|
+
@resource = Spina::Resource.find(params[:resource_id]) if params[:resource_id].present?
|
22
|
+
end
|
23
|
+
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module Spina
|
2
|
+
module Api
|
3
|
+
class ResourcesController < ApiController
|
4
|
+
include Paginable
|
5
|
+
|
6
|
+
def index
|
7
|
+
resources = Resource.order(:id)
|
8
|
+
render json: Spina::Api::ResourceSerializer.new(*pagination(resources)).serializable_hash.to_json
|
9
|
+
end
|
10
|
+
|
11
|
+
def show
|
12
|
+
@resource = Resource.find(params[:id])
|
13
|
+
render json: Spina::Api::ResourceSerializer.new(@resource).serializable_hash.to_json
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
@@ -10,11 +10,7 @@ module Spina
|
|
10
10
|
return "" if image.nil?
|
11
11
|
|
12
12
|
# support both ImageProcessing gem macro :resize_to_limit and ImageMagick-specific :resize
|
13
|
-
resize_key =
|
14
|
-
:resize
|
15
|
-
else
|
16
|
-
:resize_to_limit
|
17
|
-
end
|
13
|
+
resize_key = Spina.config.embedded_image_size.is_a?(Array) ? :resize_to_limit : :resize
|
18
14
|
main_app.url_for(image.variant(Hash[resize_key, Spina.config.embedded_image_size]))
|
19
15
|
end
|
20
16
|
|
@@ -1,16 +1,13 @@
|
|
1
1
|
module Spina::SpinaHelper
|
2
2
|
|
3
|
-
def
|
3
|
+
def spina_importmap_tags
|
4
4
|
safe_join [
|
5
|
-
|
6
|
-
|
7
|
-
javascript_include_tag("
|
8
|
-
|
5
|
+
javascript_inline_importmap_tag(Spina.config.importmap),
|
6
|
+
javascript_importmap_shim_tag,
|
7
|
+
javascript_include_tag("spina/libraries/trix"),
|
8
|
+
javascript_import_module_tag("application")
|
9
9
|
], "\n"
|
10
10
|
end
|
11
11
|
|
12
|
-
def autoloader_include_tag
|
13
|
-
javascript_include_tag("stimulus/loaders/autoloader", type: "module-shim")
|
14
|
-
end
|
15
12
|
|
16
13
|
end
|
data/app/models/spina/page.rb
CHANGED
@@ -0,0 +1,20 @@
|
|
1
|
+
module Spina::Api
|
2
|
+
class ImageSerializer < BaseSerializer
|
3
|
+
set_type :image
|
4
|
+
|
5
|
+
attributes :id
|
6
|
+
|
7
|
+
attribute :original_url do |image, params|
|
8
|
+
params[:view_context].main_app.url_for(image.file)
|
9
|
+
end
|
10
|
+
|
11
|
+
attribute :thumbnail_url do |image, params|
|
12
|
+
params[:view_context].main_app.url_for(image.variant(resize_to_fill: Spina.config.thumbnail_image_size))
|
13
|
+
end
|
14
|
+
|
15
|
+
attribute :embedded_image_size_url do |image, params|
|
16
|
+
resize_key = Spina.config.embedded_image_size.is_a?(Array) ? :resize_to_limit : :resize
|
17
|
+
params[:view_context].main_app.url_for(image.variant(Hash[resize_key, Spina.config.embedded_image_size]))
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
module Spina::Api
|
2
|
+
class NavigationSerializer < BaseSerializer
|
3
|
+
set_type :navigation
|
4
|
+
|
5
|
+
attributes :name, :label
|
6
|
+
|
7
|
+
attribute :tree do |navigation|
|
8
|
+
items_to_tree(navigation.navigation_items.sorted.roots.in_menu.live.joins(:page))
|
9
|
+
end
|
10
|
+
|
11
|
+
class << self
|
12
|
+
|
13
|
+
def items_to_tree(collection)
|
14
|
+
collection.map do |item|
|
15
|
+
{
|
16
|
+
depth: item.depth,
|
17
|
+
page: {
|
18
|
+
id: item.page_id,
|
19
|
+
menu_title: item.menu_title,
|
20
|
+
materialized_path: item.materialized_path
|
21
|
+
},
|
22
|
+
children: items_to_tree(item.children.sorted.in_menu.live.joins(:page))
|
23
|
+
}
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
module Spina::Api
|
2
|
+
class PageSerializer < BaseSerializer
|
3
|
+
set_type :page
|
4
|
+
|
5
|
+
attributes :title, :seo_title, :menu_title, :materialized_path, :name, :description, :view_template
|
6
|
+
|
7
|
+
attribute(:content) { |page| page_content(page) }
|
8
|
+
|
9
|
+
belongs_to :resource
|
10
|
+
|
11
|
+
class << self
|
12
|
+
|
13
|
+
def page_content(page)
|
14
|
+
return [] unless view_template(page)
|
15
|
+
|
16
|
+
view_template(page)[:parts].map do |part|
|
17
|
+
{ part => page.content(part) }
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def view_template(page)
|
22
|
+
Spina::Current.theme.view_templates.find{|view_template| view_template[:name] == page.view_template}
|
23
|
+
end
|
24
|
+
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
module Spina::Api
|
2
|
+
class ResourceSerializer < BaseSerializer
|
3
|
+
set_type :resource
|
4
|
+
|
5
|
+
attributes :name, :label, :view_template, :order_by, :slug
|
6
|
+
|
7
|
+
has_many :pages, lazy_load_data: true, links: {
|
8
|
+
self: -> (object) { api_resource_path(object.id) },
|
9
|
+
related: -> (object) { api_resource_pages_path(object.id) }
|
10
|
+
}, meta: -> (resource) { {count: resource.pages.live.length} }
|
11
|
+
end
|
12
|
+
end
|
@@ -10,19 +10,15 @@
|
|
10
10
|
|
11
11
|
<title>Spina CMS</title>
|
12
12
|
|
13
|
-
<!-- Tailwind -->
|
13
|
+
<!-- Tailwind -->
|
14
14
|
<%= stylesheet_link_tag 'spina/application', data: {turbolinks_track: true} %>
|
15
15
|
|
16
|
-
<!--
|
17
|
-
<%=
|
18
|
-
<%= spina_include_tags %>
|
16
|
+
<!-- Spina's importmap -->
|
17
|
+
<%= spina_importmap_tags %>
|
19
18
|
|
20
19
|
<!-- Plugins & Hooks -->
|
21
20
|
<%= yield(:head) %>
|
22
21
|
<%= render Spina::Hooks::HookComponent.new(partial: "head") %>
|
23
|
-
|
24
|
-
<!-- Stimulus Autoloader -->
|
25
|
-
<%= autoloader_include_tag %>
|
26
22
|
</head>
|
27
23
|
|
28
24
|
<body>
|
@@ -17,8 +17,8 @@
|
|
17
17
|
<%= render Spina::MainNavigation::LinkComponent.new t('spina.website.pages'), spina.admin_pages_path, active: controller_name.in?(%w(pages resources)) %>
|
18
18
|
|
19
19
|
<%= render Spina::MainNavigation::LinkComponent.new t('spina.navigations.navigations'), spina.admin_navigations_path, active: controller_name == "navigations" %>
|
20
|
-
|
21
|
-
<%= render Spina::MainNavigation::LinkComponent.new
|
20
|
+
|
21
|
+
<%= render Spina::MainNavigation::LinkComponent.new t('spina.layout.layout'), spina.edit_admin_layout_path, active: controller_name == "layout" %>
|
22
22
|
|
23
23
|
<%= render Spina::MainNavigation::LinkComponent.new t('spina.website.media_library'), spina.admin_images_path, active: controller_name.in?(%w(images media_folders attachments)) %>
|
24
24
|
|
data/config/locales/ru.yml
CHANGED
@@ -6,9 +6,9 @@ ru:
|
|
6
6
|
city: Город
|
7
7
|
email: Почта
|
8
8
|
facebook: Facebook
|
9
|
-
google_analytics: Google
|
9
|
+
google_analytics: Google Аналитика
|
10
10
|
google_plus: Google+
|
11
|
-
google_site_verification:
|
11
|
+
google_site_verification: Проверка сайта Google
|
12
12
|
instagram: Instagram
|
13
13
|
kvk_identifier: Торговая палата
|
14
14
|
kvk_identifier_description: Торговая палата
|
@@ -28,16 +28,16 @@ ru:
|
|
28
28
|
name: Название файла
|
29
29
|
size: Размер
|
30
30
|
spina/media_folder:
|
31
|
-
name:
|
31
|
+
name: Имя
|
32
32
|
spina/navigation:
|
33
|
-
auto_add_pages:
|
34
|
-
auto_add_pages_description:
|
35
|
-
label:
|
36
|
-
pages:
|
37
|
-
pages_description:
|
33
|
+
auto_add_pages: Автоматически добавлять страницы
|
34
|
+
auto_add_pages_description: Новые страницы автоматически добавляются в эту навигацию.
|
35
|
+
label: Метка
|
36
|
+
pages: Страницы
|
37
|
+
pages_description: Выберите страницы, которые вы хотите использовать в этой навигации
|
38
38
|
spina/page:
|
39
|
-
ancestry:
|
40
|
-
created_at:
|
39
|
+
ancestry: Родительская страница
|
40
|
+
created_at: Создано в
|
41
41
|
description: Мета описание
|
42
42
|
description_description: Это описание будет показано в результатах поиска
|
43
43
|
description_placeholder: Краткое описание вашей страницы
|
@@ -48,26 +48,27 @@ ru:
|
|
48
48
|
link_url_placeholder: Например http://www.example.com/
|
49
49
|
menu_title: Навигация
|
50
50
|
menu_title_placeholder: Оставьте пустым, чтобы использовать заголовок страницы
|
51
|
-
no_parent:
|
52
|
-
resource:
|
51
|
+
no_parent: Нет родителя
|
52
|
+
resource: Ресурс
|
53
53
|
seo_title: SEO <title>
|
54
|
-
seo_title_description:
|
54
|
+
seo_title_description: Убедитесь, что ваш результат поиска хорошо выглядит в поисковых системах
|
55
55
|
seo_title_placeholder: Это название используется в <title>-tag
|
56
56
|
show_in_menu: Показать в навигации
|
57
|
-
show_in_menu_description: При выключении эта страница не будет показана в
|
57
|
+
show_in_menu_description: При выключении эта страница не будет показана в
|
58
|
+
навигации
|
58
59
|
skip_to_first_child: Перенаправление
|
59
|
-
skip_to_first_child_description: Переход на страницу
|
60
|
+
skip_to_first_child_description: Переход на дочернюю страницу
|
60
61
|
title: Заголовок
|
61
62
|
title_placeholder: Заголовок страницы
|
62
|
-
url_title:
|
63
|
-
url_title_description:
|
64
|
-
url_title_placeholder:
|
63
|
+
url_title: Переопределить слаг
|
64
|
+
url_title_description: Опционально
|
65
|
+
url_title_placeholder: Слаг
|
65
66
|
view_template: Шаблон страницы
|
66
67
|
spina/resource:
|
67
|
-
label:
|
68
|
-
order_by:
|
69
|
-
parent_page:
|
70
|
-
view_template:
|
68
|
+
label: Метка
|
69
|
+
order_by: Сортировать по
|
70
|
+
parent_page: Родительская страница
|
71
|
+
view_template: Шаблон представления по умолчанию
|
71
72
|
spina/user:
|
72
73
|
admin: Администратор
|
73
74
|
admin_description: Администраторы могут создавать пользователей
|
@@ -104,19 +105,21 @@ ru:
|
|
104
105
|
other: Пользователей
|
105
106
|
spina:
|
106
107
|
accounts:
|
107
|
-
contact_details:
|
108
|
-
contact_details_description:
|
109
|
-
couldnt_be_saved:
|
110
|
-
name_description:
|
111
|
-
save:
|
112
|
-
saved:
|
108
|
+
contact_details: Контактная информация
|
109
|
+
contact_details_description: Электронная почта и телефон
|
110
|
+
couldnt_be_saved: Аккаунт не может быть сохранен
|
111
|
+
name_description: Название вашего веб-сайта
|
112
|
+
save: Сохранить аккаунт
|
113
|
+
saved: Аккаунт сохранен
|
113
114
|
ago: назад
|
114
115
|
attachments:
|
115
|
-
choose_attachment:
|
116
|
-
delete_confirmation_html:
|
116
|
+
choose_attachment: Выберите вложение
|
117
|
+
delete_confirmation_html: Вы уверены? Это вложение <span class='font-semibold'>может</span>
|
118
|
+
использоваться на странице.
|
119
|
+
download: Скачать
|
117
120
|
insert: Вставить документ
|
118
121
|
insert_multiple: Вставить документы
|
119
|
-
upload:
|
122
|
+
upload: Загрузить файлы
|
120
123
|
cancel: Отмена
|
121
124
|
choose_from_library: Выбрать из библиотеки
|
122
125
|
close: Закрыть
|
@@ -125,159 +128,171 @@ ru:
|
|
125
128
|
edit: Редактировать
|
126
129
|
edit_website: Редактировать сайт
|
127
130
|
forgot_password:
|
128
|
-
expired:
|
129
|
-
mail_subject:
|
130
|
-
new:
|
131
|
-
request:
|
132
|
-
save:
|
133
|
-
success:
|
134
|
-
unknown_user:
|
131
|
+
expired: Срок действия вашего токена для сброса пароля истек
|
132
|
+
mail_subject: Сбросить пароль
|
133
|
+
new: Забыли пароль
|
134
|
+
request: Запросить новый пароль
|
135
|
+
save: Сохранить новый пароль
|
136
|
+
success: Вы можете использовать свой новый пароль
|
137
|
+
unknown_user: Этот пользователь не существует
|
135
138
|
images:
|
136
|
-
all_images:
|
137
|
-
back:
|
138
|
-
cannot_be_created:
|
139
|
-
choose_image:
|
140
|
-
choose_images:
|
141
|
-
confirm_selection:
|
142
|
-
delete:
|
143
|
-
delete_confirmation_html:
|
144
|
-
delete_folder:
|
145
|
-
done_organizing:
|
146
|
-
insert_image:
|
147
|
-
insert_photo:
|
148
|
-
insert_photos:
|
149
|
-
link:
|
150
|
-
new_folder:
|
151
|
-
organize:
|
152
|
-
remove_image:
|
153
|
-
upload:
|
154
|
-
upload_image:
|
139
|
+
all_images: Все изображения
|
140
|
+
back: Назад
|
141
|
+
cannot_be_created: Не может быть создано
|
142
|
+
choose_image: Выбрать изображение
|
143
|
+
choose_images: Выбрать изображения
|
144
|
+
confirm_selection: Подтвердите выбор
|
145
|
+
delete: Удалить
|
146
|
+
delete_confirmation_html: Вы действительно хотите удалить это <strong>изображение</strong>?
|
147
|
+
delete_folder: Удалить папку
|
148
|
+
done_organizing: Готово
|
149
|
+
insert_image: Вставить изображение
|
150
|
+
insert_photo: Вставить фото
|
151
|
+
insert_photos: Вставить фото
|
152
|
+
link: Ссылка на сайт
|
153
|
+
new_folder: Новая папка
|
154
|
+
organize: Организовать
|
155
|
+
remove_image: Удалить изображение
|
156
|
+
upload: Загрузить изображения
|
157
|
+
upload_image: Загрузить изображение
|
155
158
|
languages:
|
156
|
-
bg:
|
157
|
-
de:
|
159
|
+
bg: Болгарский
|
160
|
+
de: Немецкий
|
158
161
|
en: Английский
|
159
|
-
es:
|
160
|
-
fr:
|
161
|
-
id:
|
162
|
-
it:
|
162
|
+
es: Испанский
|
163
|
+
fr: Французский
|
164
|
+
id: Индонезийский
|
165
|
+
it: Итальянский
|
163
166
|
nl: Голландский
|
164
|
-
pl:
|
165
|
-
pt-BR:
|
166
|
-
ro:
|
167
|
-
ru:
|
168
|
-
sv:
|
169
|
-
th:
|
170
|
-
tr:
|
171
|
-
zh-CN:
|
167
|
+
pl: Польский
|
168
|
+
pt-BR: Бразильский португальский
|
169
|
+
ro: Румынский
|
170
|
+
ru: Русский
|
171
|
+
sv: Шведский
|
172
|
+
th: Тайский
|
173
|
+
tr: Турецкий
|
174
|
+
zh-CN: Упрощенный китайский
|
172
175
|
layout:
|
173
|
-
couldnt_be_saved:
|
174
|
-
layout:
|
175
|
-
no_layout_parts:
|
176
|
-
save:
|
177
|
-
saved:
|
176
|
+
couldnt_be_saved: Макет не может быть сохранен
|
177
|
+
layout: Макет
|
178
|
+
no_layout_parts: Нет доступных частей макета
|
179
|
+
save: Сохранить макет
|
180
|
+
saved: Макет сохранен
|
178
181
|
login: Логин
|
179
182
|
logout: Выход
|
180
183
|
main_menu: Главное меню
|
181
184
|
media_library:
|
182
|
-
add_folder:
|
183
|
-
add_image:
|
185
|
+
add_folder: Добавить папку
|
186
|
+
add_image: Добавить изображение
|
184
187
|
attachments: Документы
|
185
|
-
back_to_all:
|
186
|
-
filename:
|
187
|
-
images:
|
188
|
-
images_count:
|
189
|
-
|
190
|
-
|
191
|
-
|
188
|
+
back_to_all: Назад ко всем
|
189
|
+
filename: Имя файла
|
190
|
+
images: Изображения
|
191
|
+
images_count:
|
192
|
+
one: "%{count} изображение"
|
193
|
+
few: "%{count} изображения"
|
194
|
+
many: "%{count} изображений"
|
195
|
+
other: "%{count} изображений"
|
196
|
+
zero: нет изображений
|
197
|
+
insert: Вставить изображение
|
198
|
+
media_folder_delete_confirmation_html: Вы уверены? Изображения <strong>не</strong>
|
199
|
+
будут удалены.
|
200
|
+
no_folder: Нет папки
|
192
201
|
photos: Изображения
|
193
|
-
rename_folder:
|
194
|
-
save_media_folder:
|
195
|
-
upload_from_device:
|
196
|
-
uploading:
|
202
|
+
rename_folder: Переименовать папку
|
203
|
+
save_media_folder: Сохранить папку мультимедиа
|
204
|
+
upload_from_device: Загрузить с устройства
|
205
|
+
uploading: Загрузка...
|
197
206
|
modal:
|
198
207
|
agree: Да, я уверен
|
199
208
|
cancel: Нет, отменить
|
200
209
|
navigations:
|
201
|
-
add_menu_item:
|
202
|
-
add_sub_item:
|
203
|
-
choose_page:
|
204
|
-
delete_item:
|
205
|
-
delete_item_confirmation_html:
|
206
|
-
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
+
add_menu_item: Добавить пункт меню
|
211
|
+
add_sub_item: Добавить подпункт
|
212
|
+
choose_page: Выбрать страницу
|
213
|
+
delete_item: Удалить пункт
|
214
|
+
delete_item_confirmation_html: Вы уверены, что хотите <span class='font-semibold'>удалить</span>
|
215
|
+
этот пункт меню?
|
216
|
+
description: Добавляйте и сортируйте элементы по своему усмотрению. Вы можете добавлять элементы вложенного меню,
|
217
|
+
но не обязательно.
|
218
|
+
navigations: Навигация
|
219
|
+
no_navigations: На этом веб-сайте еще нет навигации. Вы можете настроить её в своей
|
220
|
+
конфигурации темы.
|
221
|
+
sorting_saved: Сортировка сохранена
|
210
222
|
notifications:
|
211
223
|
alert: Упс! Что-то пошло не так
|
212
224
|
information: Информация
|
213
225
|
login: Вы должны войти
|
214
226
|
wrong_username_or_password: Неправильная почта или пароль
|
215
227
|
options:
|
216
|
-
choose_option:
|
228
|
+
choose_option: Выберите вариант
|
217
229
|
pages:
|
218
|
-
add_page_to:
|
219
|
-
add_translation:
|
230
|
+
add_page_to: 'Добавить страницу в:'
|
231
|
+
add_translation: Добавить перевод %{language}
|
220
232
|
advanced: Дополнительно
|
221
|
-
cannot_be_deleted:
|
233
|
+
cannot_be_deleted: Страница не может быть удалена
|
222
234
|
change_order: Изменить порядок
|
223
|
-
change_view_template:
|
224
|
-
change_view_template_confirmation:
|
235
|
+
change_view_template: Change view template
|
236
|
+
change_view_template_confirmation: Вы уверены, что хотите сменить шаблон страницы?
|
237
|
+
Содержимое страницы, которое не входит в новый шаблон, будет потеряно.
|
225
238
|
concept: Концепция
|
226
|
-
create:
|
239
|
+
create: Создать страницу
|
227
240
|
create_page: Создать %{template}
|
228
|
-
delete:
|
241
|
+
delete: Удалить страницу
|
229
242
|
delete_confirmation: Вы уверены, что хотите удалить страницу <strong>%{subject}</strong>?
|
230
|
-
deleted:
|
243
|
+
deleted: Страница удалена
|
231
244
|
done_changing_order: Порядок изменен
|
232
|
-
edit_translation:
|
245
|
+
edit_translation: Редактировать перевод %{language}
|
233
246
|
invisible_to_search_engines: Ваш сайт не виден для поисковых машин
|
234
|
-
invisible_to_search_engines_description: Перейти к вашим параметрам, чтобы активировать
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
247
|
+
invisible_to_search_engines_description: Перейти к вашим параметрам, чтобы активировать
|
248
|
+
поисковые системы.
|
249
|
+
main_collection: Основная коллекция
|
250
|
+
materialize_path_confirmation: Вы уверены, что хотите перестроить путь для
|
251
|
+
этой страницы?
|
252
|
+
missing_translations: Отсутствующие переводы
|
253
|
+
move_page: Переместить страницу
|
254
|
+
moved: Страница перемещена
|
240
255
|
new: Новая страница
|
241
|
-
no_pages_yet:
|
242
|
-
no_parent_page:
|
256
|
+
no_pages_yet: Страниц пока нет
|
257
|
+
no_parent_page: Нет родительской страницы
|
243
258
|
page_content: Контент
|
244
259
|
page_part: Раздел страницы
|
245
260
|
page_seo: Поисковые системы
|
246
|
-
path:
|
261
|
+
path: 'Путь:'
|
247
262
|
photo_picker: Выбрать изображение
|
248
263
|
photos_picker: Выбрать изображения
|
249
|
-
preview:
|
250
|
-
publish:
|
251
|
-
published:
|
252
|
-
rebuild_materialized_path:
|
253
|
-
recommended:
|
264
|
+
preview: Предварительный просмотр
|
265
|
+
publish: Публиковать
|
266
|
+
published: Страница опубликована
|
267
|
+
rebuild_materialized_path: Перестроить материализованный путь
|
268
|
+
recommended: рекомендуемые
|
254
269
|
save: Сохранить страницу
|
255
|
-
save_changes:
|
256
|
-
save_draft:
|
257
|
-
saved:
|
258
|
-
saving:
|
259
|
-
search_engines:
|
270
|
+
save_changes: Сохранить изменения
|
271
|
+
save_draft: Сохранить черновик
|
272
|
+
saved: Страница сохранена
|
273
|
+
saving: Сохранение...
|
274
|
+
search_engines: Поисковые системы
|
260
275
|
show_in_menu: Невидимый
|
261
|
-
skip_to_first_child: Переход на страницу
|
262
|
-
sorting_saved:
|
276
|
+
skip_to_first_child: Переход на дочернюю страницу
|
277
|
+
sorting_saved: Сортировка сохранена
|
263
278
|
permanently_delete: Удалить навсегда
|
264
279
|
photos:
|
265
280
|
cannot_be_created: 'Изображение не может быть обработано:'
|
266
281
|
choose_images: Выбрать изображения
|
267
|
-
delete:
|
282
|
+
delete: Удалить
|
268
283
|
delete_confirmation: Вы уверены, что хотите удалить <strong>image</strong>?
|
269
|
-
delete_folder:
|
270
|
-
done_organizing:
|
284
|
+
delete_folder: Удалить папку
|
285
|
+
done_organizing: Готово
|
271
286
|
insert_photo: Вставить изображение
|
272
287
|
insert_photos: Вставить изображения
|
273
288
|
link: 'URL изображения:'
|
274
|
-
new_folder:
|
275
|
-
organize:
|
276
|
-
rename_folder:
|
277
|
-
select_images:
|
278
|
-
upload_image:
|
289
|
+
new_folder: Новая папка
|
290
|
+
organize: Организовать изображения
|
291
|
+
rename_folder: Переименовать папку
|
292
|
+
select_images: Выбрать изображения
|
293
|
+
upload_image: Загрузите изображение
|
279
294
|
preferences:
|
280
|
-
Analytics:
|
295
|
+
Analytics: Аналитика
|
281
296
|
account: Общее
|
282
297
|
account_description: Персональные параметры
|
283
298
|
account_save: Сохранить параметры
|
@@ -297,66 +312,73 @@ ru:
|
|
297
312
|
users_description: Управление пользователями и администраторами
|
298
313
|
preview_website: Предварительный просмотр сайта
|
299
314
|
resources:
|
300
|
-
edit:
|
301
|
-
label_description:
|
302
|
-
manual_sorting:
|
303
|
-
no_default_template:
|
304
|
-
saved:
|
305
|
-
settings:
|
306
|
-
settings_description:
|
307
|
-
|
315
|
+
edit: Редактировать ресурс
|
316
|
+
label_description: Ярлык для пользователя, для этой коллекции страниц.
|
317
|
+
manual_sorting: Ручная сортировка
|
318
|
+
no_default_template: Нет шаблона по умолчанию
|
319
|
+
saved: Коллекция страниц сохранена
|
320
|
+
settings: "%{label} настройки"
|
321
|
+
settings_description: Перед всеми страницами в этой коллекции будет стоять
|
322
|
+
этот слаг.
|
323
|
+
save: Сохранить
|
308
324
|
search: Поиск...
|
309
325
|
settings:
|
310
|
-
|
311
|
-
|
326
|
+
general: Общие
|
327
|
+
save: Сохранить настройки
|
328
|
+
title: Настройки
|
329
|
+
users: Пользователи
|
312
330
|
theme:
|
313
|
-
save:
|
314
|
-
saved:
|
315
|
-
theme:
|
316
|
-
theme_description:
|
331
|
+
save: Сохранить тему
|
332
|
+
saved: Тема сохранена
|
333
|
+
theme: Тема
|
334
|
+
theme_description: Настройте свою тему
|
317
335
|
ui:
|
318
|
-
cancel:
|
319
|
-
delete:
|
320
|
-
load_more:
|
321
|
-
move_to:
|
322
|
-
new_entry:
|
323
|
-
optional:
|
324
|
-
rename:
|
325
|
-
save_changes:
|
326
|
-
saving:
|
336
|
+
cancel: Отмена
|
337
|
+
delete: Удалить
|
338
|
+
load_more: Загрузи больше
|
339
|
+
move_to: Перенести в
|
340
|
+
new_entry: Новая запись
|
341
|
+
optional: По желанию
|
342
|
+
rename: Переименовать
|
343
|
+
save_changes: Сохранить изменения
|
344
|
+
saving: Сохранение...
|
327
345
|
users:
|
328
|
-
authorization:
|
329
|
-
authorization_description:
|
346
|
+
authorization: Авторизация
|
347
|
+
authorization_description: Администраторы могут управлять пользователями. Обычные пользователи не могут.
|
330
348
|
cannot_be_created: Пользователь не сохранен
|
331
|
-
delete:
|
349
|
+
delete: Удалить пользователя
|
332
350
|
delete_confirmation_html: Вы уверены, что хотите удалить пользователя <strong>%{user}</strong>?
|
333
|
-
deleted:
|
334
|
-
last_login:
|
335
|
-
never_logged_in:
|
351
|
+
deleted: Пользователь удален
|
352
|
+
last_login: 'Последний визит:'
|
353
|
+
never_logged_in: Никогда не входил в систему
|
336
354
|
new: Новый пользователь
|
337
|
-
profile:
|
338
|
-
profile_description:
|
355
|
+
profile: Профиль
|
356
|
+
profile_description: Эта информация будет использоваться для идентификации разных пользователей.
|
357
|
+
Пользователи будут использовать свой адрес электронной почты для входа в систему.
|
339
358
|
save: Сохранить пользователя
|
340
|
-
saved:
|
341
|
-
visit_page:
|
359
|
+
saved: Пользователь сохранен
|
360
|
+
visit_page: Посетите страницу
|
342
361
|
website:
|
343
|
-
all_pages:
|
362
|
+
all_pages: Все страницы
|
363
|
+
content: Содержание
|
344
364
|
documents: Документы
|
345
|
-
images:
|
365
|
+
images: Картинки
|
346
366
|
media_library: Медиа библиотека
|
347
367
|
media_library_description: Здесь вы найдете все ваши изображения и документы
|
348
368
|
pages: Страницы
|
349
369
|
pages_description: Все страницы вашего сайта
|
350
370
|
photos: Изображения
|
371
|
+
settings: Настройки
|
372
|
+
theme: Тема
|
351
373
|
title: Ваш сайт
|
352
374
|
wysiwyg:
|
353
375
|
heading_1: Заголовок 1
|
354
376
|
heading_2: Заголовок 2
|
355
377
|
heading_3: Заголовок 3
|
356
378
|
insert_link: Вставить ссылку
|
357
|
-
link:
|
379
|
+
link: Ссылка
|
358
380
|
paragraph: Параграф
|
359
381
|
quote: Цитата
|
360
|
-
unlink:
|
361
|
-
url:
|
362
|
-
url_placeholder:
|
382
|
+
unlink: Удалить ссылку
|
383
|
+
url: URL
|
384
|
+
url_placeholder: Введите URL
|