feat: add show author option to portal settings and update related views (#225)
* feat: add show author option to portal settings and update related views * fix: update portal reference to use local variable for show author condition * feat: enhance show_author handling in portal config and add related tests
This commit is contained in:
parent
c026ee2fc8
commit
21007bd20b
@ -23,7 +23,7 @@ class Api::V1::Accounts::PortalsController < Api::V1::Accounts::BaseController
|
||||
|
||||
def update
|
||||
ActiveRecord::Base.transaction do
|
||||
@portal.update!(portal_params.merge(live_chat_widget_params)) if params[:portal].present?
|
||||
@portal.update!(merged_portal_params.merge(live_chat_widget_params)) if params[:portal].present?
|
||||
# @portal.custom_domain = parsed_custom_domain
|
||||
process_attached_logo if params[:blob_id].present?
|
||||
rescue ActiveRecord::RecordInvalid => e
|
||||
@ -79,10 +79,20 @@ class Api::V1::Accounts::PortalsController < Api::V1::Accounts::BaseController
|
||||
def portal_params
|
||||
params.require(:portal).permit(
|
||||
:id, :color, :custom_domain, :header_text, :homepage_link,
|
||||
:name, :page_title, :slug, :archived, { config: [:default_locale, { allowed_locales: [] }] }
|
||||
:name, :page_title, :slug, :archived, { config: [:default_locale, :show_author, { allowed_locales: [] }] }
|
||||
)
|
||||
end
|
||||
|
||||
def merged_portal_params
|
||||
update_params = portal_params.to_h
|
||||
if update_params.key?('config')
|
||||
base_config = @portal.config.is_a?(Hash) ? @portal.config : {}
|
||||
incoming_config = update_params['config']
|
||||
update_params['config'] = incoming_config.is_a?(Hash) ? base_config.merge(incoming_config) : base_config
|
||||
end
|
||||
update_params
|
||||
end
|
||||
|
||||
def live_chat_widget_params
|
||||
permitted_params = params.permit(:inbox_id)
|
||||
return {} unless permitted_params.key?(:inbox_id)
|
||||
|
||||
@ -15,6 +15,7 @@ import Input from 'dashboard/components-next/input/Input.vue';
|
||||
import Avatar from 'dashboard/components-next/avatar/Avatar.vue';
|
||||
import ComboBox from 'dashboard/components-next/combobox/ComboBox.vue';
|
||||
import ColorPicker from 'dashboard/components-next/colorpicker/ColorPicker.vue';
|
||||
import Switch from 'dashboard/components-next/switch/Switch.vue';
|
||||
|
||||
const props = defineProps({
|
||||
activePortal: {
|
||||
@ -45,6 +46,7 @@ const state = reactive({
|
||||
liveChatWidgetInboxId: '',
|
||||
logoUrl: '',
|
||||
avatarBlobId: '',
|
||||
showAuthor: true,
|
||||
});
|
||||
|
||||
const originalState = reactive({ ...state });
|
||||
@ -117,6 +119,7 @@ watch(
|
||||
homePageLink: newVal.homepage_link,
|
||||
slug: newVal.slug,
|
||||
liveChatWidgetInboxId: newVal.inbox?.id || '',
|
||||
showAuthor: newVal.config?.show_author !== false,
|
||||
});
|
||||
if (newVal.logo) {
|
||||
const {
|
||||
@ -149,6 +152,7 @@ const handleUpdatePortal = () => {
|
||||
homepage_link: state.homePageLink,
|
||||
blob_id: state.avatarBlobId,
|
||||
inbox_id: state.liveChatWidgetInboxId,
|
||||
config: { show_author: state.showAuthor },
|
||||
};
|
||||
emit('updatePortal', portal);
|
||||
};
|
||||
@ -335,6 +339,21 @@ const handleAvatarDelete = () => {
|
||||
<ColorPicker v-model="state.widgetColor" />
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="grid items-start justify-between w-full gap-2 grid-cols-[200px,1fr]"
|
||||
>
|
||||
<label
|
||||
class="text-sm font-medium whitespace-nowrap py-2.5 text-n-slate-12"
|
||||
>
|
||||
{{ t('HELP_CENTER.PORTAL_SETTINGS.FORM.SHOW_AUTHOR.LABEL') }}
|
||||
</label>
|
||||
<div class="flex flex-col gap-1 py-2.5">
|
||||
<Switch v-model="state.showAuthor" />
|
||||
<span class="text-xs text-n-slate-11">
|
||||
{{ t('HELP_CENTER.PORTAL_SETTINGS.FORM.SHOW_AUTHOR.HELP_TEXT') }}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="flex justify-end w-full gap-2">
|
||||
<Button
|
||||
:label="t('HELP_CENTER.PORTAL_SETTINGS.FORM.SAVE_CHANGES')"
|
||||
|
||||
@ -747,6 +747,10 @@
|
||||
"BRAND_COLOR": {
|
||||
"LABEL": "Brand color"
|
||||
},
|
||||
"SHOW_AUTHOR": {
|
||||
"LABEL": "Show article authors",
|
||||
"HELP_TEXT": "Display author information on category pages"
|
||||
},
|
||||
"SAVE_CHANGES": "Save changes"
|
||||
},
|
||||
"CONFIGURATION_FORM": {
|
||||
|
||||
@ -747,6 +747,10 @@
|
||||
"BRAND_COLOR": {
|
||||
"LABEL": "Cor da Marca"
|
||||
},
|
||||
"SHOW_AUTHOR": {
|
||||
"LABEL": "Mostrar autores dos artigos",
|
||||
"HELP_TEXT": "Exibir informações de autoria nas páginas de categorias"
|
||||
},
|
||||
"SAVE_CHANGES": "Salvar Alterações"
|
||||
},
|
||||
"CONFIGURATION_FORM": {
|
||||
|
||||
@ -44,7 +44,11 @@ class Portal < ApplicationRecord
|
||||
|
||||
scope :active, -> { where(archived: false) }
|
||||
|
||||
CONFIG_JSON_KEYS = %w[allowed_locales default_locale website_token].freeze
|
||||
CONFIG_JSON_KEYS = %w[allowed_locales default_locale website_token show_author].freeze
|
||||
|
||||
def show_author?
|
||||
!ActiveModel::Type::Boolean.new.cast(config['show_author']).equal?(false)
|
||||
end
|
||||
|
||||
def file_base_data
|
||||
{
|
||||
|
||||
@ -15,6 +15,7 @@ json.config do
|
||||
json.partial! 'api/v1/models/portal_config', formats: [:json], locale: locale, portal: portal
|
||||
end
|
||||
end
|
||||
json.show_author portal.show_author?
|
||||
end
|
||||
|
||||
if portal.channel_web_widget
|
||||
|
||||
@ -46,8 +46,10 @@
|
||||
</div>
|
||||
<div class="flex justify-between flex-row items-center <%= !@is_plain_layout_enabled && 'px-2' %>">
|
||||
<div class="flex flex-row items-center gap-1">
|
||||
<% if portal.show_author? %>
|
||||
<%= render "public/api/v1/portals/authors", category: category, show_expanded: false %>
|
||||
<span class="text-slate-600 dark:text-slate-400">•</span>
|
||||
<% end %>
|
||||
<span class="text-sm font-medium text-slate-600 dark:text-slate-400"><%= render 'public/api/v1/portals/article_count', article_count: category.articles.published.order(position: :asc).size %></span>
|
||||
</div>
|
||||
<div>
|
||||
|
||||
@ -22,8 +22,10 @@
|
||||
<% end %>
|
||||
</div>
|
||||
<div class="flex flex-row items-center gap-1">
|
||||
<% if portal.show_author? %>
|
||||
<%= render "public/api/v1/portals/authors", category: category, show_expanded: true %>
|
||||
<span class="text-slate-600 dark:text-slate-400">•</span>
|
||||
<% end %>
|
||||
<span class="flex items-center text-base text-slate-600 dark:text-slate-400 font-medium"><%= render 'public/api/v1/portals/article_count', article_count: category.articles.published.size %></span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@ -131,7 +131,49 @@ RSpec.describe 'Api::V1::Accounts::Portals', type: :request do
|
||||
json_response = response.parsed_body
|
||||
expect(json_response['name']).to eql(portal_params[:portal][:name])
|
||||
expect(json_response['config']).to eql({ 'allowed_locales' => [{ 'articles_count' => 0, 'categories_count' => 0, 'code' => 'en' },
|
||||
{ 'articles_count' => 0, 'categories_count' => 0, 'code' => 'es' }] })
|
||||
{ 'articles_count' => 0, 'categories_count' => 0, 'code' => 'es' }],
|
||||
'show_author' => true })
|
||||
end
|
||||
|
||||
it 'persists show_author as false when explicitly set' do
|
||||
put "/api/v1/accounts/#{account.id}/portals/#{portal.slug}",
|
||||
params: { portal: { config: { show_author: false } } },
|
||||
headers: admin.create_new_auth_token,
|
||||
as: :json
|
||||
|
||||
expect(response).to have_http_status(:success)
|
||||
json_response = response.parsed_body
|
||||
expect(json_response['config']['show_author']).to be(false)
|
||||
|
||||
portal.reload
|
||||
expect(portal.show_author?).to be(false)
|
||||
end
|
||||
|
||||
it 'preserves show_author when updating other portal fields' do
|
||||
portal.update!(config: portal.config.merge('show_author' => false))
|
||||
|
||||
put "/api/v1/accounts/#{account.id}/portals/#{portal.slug}",
|
||||
params: { portal: { name: 'renamed_portal' } },
|
||||
headers: admin.create_new_auth_token,
|
||||
as: :json
|
||||
|
||||
expect(response).to have_http_status(:success)
|
||||
portal.reload
|
||||
expect(portal.show_author?).to be(false)
|
||||
expect(portal.name).to eql('renamed_portal')
|
||||
end
|
||||
|
||||
it 'preserves show_author when updating only allowed_locales' do
|
||||
portal.update!(config: portal.config.merge('show_author' => false))
|
||||
|
||||
put "/api/v1/accounts/#{account.id}/portals/#{portal.slug}",
|
||||
params: { portal: { config: { allowed_locales: %w[en fr] } } },
|
||||
headers: admin.create_new_auth_token,
|
||||
as: :json
|
||||
|
||||
expect(response).to have_http_status(:success)
|
||||
portal.reload
|
||||
expect(portal.show_author?).to be(false)
|
||||
end
|
||||
|
||||
it 'archive portal' do
|
||||
|
||||
Loading…
Reference in New Issue
Block a user