Skip to content

Commit 08fc8b4

Browse files
committed
add issue/58577
1 parent 9ba1cf3 commit 08fc8b4

13 files changed

Lines changed: 531 additions & 1 deletion

File tree

modules/weko-gridlayout/tests/test_admin.py

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,31 @@ def test_index_WidgetDesign(i18n_app, view_instance):
212212
pass
213213

214214

215+
# WidgetDesign.preview_view
216+
def test_preview_view_WidgetDesign(i18n_app, view_instance):
217+
test = WidgetDesign()
218+
test.admin = MagicMock()
219+
i18n_app.config["WEKO_THEME_DEFAULT_COMMUNITY"] = "0"
220+
i18n_app.config["WEKO_THEME_PREVIEW_WIDGET_DESIGN"] = (
221+
"weko_theme/preview_widget_design.html"
222+
)
223+
return_data = {
224+
"community_id": "",
225+
"detail_condition": "",
226+
"width": "3",
227+
"height": "",
228+
"index_link_list": [],
229+
"index_link_enabled": False,
230+
"community": None,
231+
"display_facet_search": False,
232+
"display_index_tree": True,
233+
"display_community": True,
234+
}
235+
with patch("weko_gridlayout.admin.get_weko_contents", return_value=return_data):
236+
with patch("flask_admin.base.render_template", return_value="dummy"):
237+
assert test.preview_view()
238+
239+
215240
# WidgetSettingView.index_view ~ ERROR
216241
def test_index_view_WidgetSettingView(i18n_app, view_instance):
217242
assert view_instance.index_view() != None

modules/weko-gridlayout/tests/test_services.py

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -287,6 +287,85 @@ def test_get_widget_list(i18n_app, widget_items):
287287
assert WidgetDesignServices.get_widget_list(repository_id, default_language)
288288

289289

290+
# def get_widget_item_list(cls, repository_id):
291+
def test_get_widget_item_list(i18n_app, widget_items):
292+
repository_id = "Root Index"
293+
WEKO_GRIDLAYOUT_ACCESS_COUNTER_TYPE = "Access counter"
294+
WEKO_GRIDLAYOUT_NOTICE_TYPE = "Notice"
295+
return_data1 = {
296+
"widget_id": 1,
297+
"repository_id": "Root Index",
298+
"widget_type": WEKO_GRIDLAYOUT_ACCESS_COUNTER_TYPE,
299+
"is_enabled": True,
300+
"is_deleted": False,
301+
"updated": 1772664727.379901,
302+
"settings": {
303+
"background_color": "test",
304+
"label_enable": True,
305+
"theme": "default",
306+
"frame_border_color": "test",
307+
"border_style": "double",
308+
"label_text_color": "test",
309+
"label_color": "test",
310+
"access_counter": "0",
311+
"following_message": "test",
312+
"other_message": "test",
313+
"preceding_message": "test",
314+
"count_start_date": "test",
315+
"multiLangSetting": {
316+
"ja": "ja"
317+
}
318+
}
319+
}
320+
return_data2 = {
321+
"widget_id":2,
322+
"repository_id": "Root Index",
323+
"widget_type": WEKO_GRIDLAYOUT_NOTICE_TYPE,
324+
"is_enabled": True,
325+
"is_deleted": False,
326+
"updated": 1772664727.379901,
327+
"settings": {
328+
"background_color": "test",
329+
"border_style": "double",
330+
"frame_border_color": "test",
331+
"hide_the_rest": "None",
332+
"label_color": "test",
333+
"label_enable": True,
334+
"label_text_color": "test",
335+
"read_more": "None",
336+
"theme": "default",
337+
"multiLangSetting": {
338+
"ja": "ja"
339+
}
340+
}
341+
}
342+
with patch(
343+
"weko_gridlayout.services.WidgetItemServices.get_widget_data_by_widget_id",
344+
return_value=return_data1,
345+
):
346+
assert WidgetDesignServices.get_widget_item_list(repository_id)
347+
348+
return_data1["settings"]["multiLangSetting"] = {"en": "en"}
349+
assert WidgetDesignServices.get_widget_item_list(repository_id)
350+
351+
return_data1["settings"]["multiLangSetting"] = {"xx": "xx"}
352+
assert WidgetDesignServices.get_widget_item_list(repository_id)
353+
354+
return_data1["settings"]["multiLangSetting"] = None
355+
assert WidgetDesignServices.get_widget_item_list(repository_id)
356+
357+
with patch('weko_gridlayout.services.isinstance', side_effect=Exception('')):
358+
assert WidgetDesignServices.get_widget_item_list(repository_id)
359+
with patch(
360+
"weko_gridlayout.services.WidgetItemServices.get_widget_data_by_widget_id",
361+
return_value=return_data2,
362+
):
363+
assert WidgetDesignServices.get_widget_item_list(repository_id)
364+
with patch("weko_gridlayout.services.WidgetItem.query") as mock_query:
365+
mock_query.return_value.filter_by.return_value.all.return_value = None
366+
assert WidgetDesignServices.get_widget_item_list(repository_id)
367+
368+
290369
# def get_widget_preview(cls, repository_id, default_language,
291370
def test_get_widget_preview(i18n_app, widget_item):
292371
repository_id = "Root Index"

modules/weko-gridlayout/tests/test_views.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -485,6 +485,16 @@ def test_delete_widget_item(client, users):
485485
assert res.status_code == 200
486486

487487

488+
# def get_widget_item_list()
489+
def test_get_widget_item_list(client, users):
490+
login_user_via_session(client=client, email=users[2]['obj'].email)
491+
res = client.get(
492+
url_for("weko_gridlayout_api.get_widget_item_list"),
493+
headers={"Content-Type": "application/json"}
494+
)
495+
assert res.status_code == 200
496+
497+
488498
# def get_account_role():
489499
def test_get_account_role(client, users):
490500
login_user_via_session(client=client, email=users[2]['obj'].email)

modules/weko-gridlayout/weko_gridlayout/admin.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,9 @@
4040
from jinja2 import contextfunction
4141
from sqlalchemy import func
4242
from wtforms.fields import StringField
43+
from weko_theme.utils import get_design_layout, \
44+
get_weko_contents, has_widget_design
45+
from invenio_i18n.ext import current_i18n
4346

4447
from . import config
4548
from .models import WidgetItem, WidgetMultiLangData
@@ -56,6 +59,23 @@ def index(self):
5659
current_app.config["WEKO_GRIDLAYOUT_ADMIN_WIDGET_DESIGN"]
5760
)
5861

62+
@expose('/preview/')
63+
def preview_view(self):
64+
# For preview page, always use main layout
65+
page, render_widgets = get_design_layout(
66+
current_app.config['WEKO_THEME_DEFAULT_COMMUNITY'])
67+
render_header_footer = has_widget_design(
68+
current_app.config['WEKO_THEME_DEFAULT_COMMUNITY'],
69+
current_i18n.language)
70+
page = None
71+
72+
return self.render(
73+
current_app.config["WEKO_THEME_PREVIEW_WIDGET_DESIGN"],
74+
page=page,
75+
render_widgets=render_widgets,
76+
render_header_footer=render_header_footer,
77+
**get_weko_contents(request.args))
78+
5979

6080
class WidgetSettingView(ModelView):
6181
"""Widget Setting admin view."""

modules/weko-gridlayout/weko_gridlayout/services.py

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -501,6 +501,60 @@ def get_widget_list(cls, repository_id, default_language):
501501

502502
return result
503503

504+
@classmethod
505+
def get_widget_item_list(cls, repository_id):
506+
"""Get Widget Item list.
507+
508+
:param repository_id: Identifier of the repository.
509+
:return: Widget Item list.
510+
"""
511+
result = {
512+
"data": {},
513+
"error": ""
514+
}
515+
try:
516+
with db.session.no_autoflush:
517+
widget_item_list = WidgetItem.query.filter_by(
518+
repository_id=str(repository_id), is_enabled=True,
519+
is_deleted=False
520+
).all()
521+
current_lang = current_i18n.language
522+
if isinstance(widget_item_list, list):
523+
for widget_item in widget_item_list:
524+
data = dict()
525+
data_display = dict()
526+
widget_item_data = \
527+
WidgetItemServices.get_widget_data_by_widget_id(
528+
widget_item.widget_id)
529+
settings = widget_item_data.get('settings')
530+
settings["widget_id"] = widget_item_data.get('widget_id')
531+
settings["id"] = widget_item_data.get('repository_id')
532+
settings["type"] = widget_item_data.get('widget_type')
533+
if settings.get('type') == WEKO_GRIDLAYOUT_ACCESS_COUNTER_TYPE:
534+
today = date.today().strftime("%Y-%m-%d")
535+
settings['created_date'] = today
536+
languages = settings.get("multiLangSetting")
537+
if (isinstance(languages, dict)
538+
and current_lang is not None):
539+
if languages.get(current_lang):
540+
data_display = languages[current_lang]
541+
elif languages.get('en'):
542+
data_display = languages['en']
543+
else:
544+
data_display["label"] = \
545+
WEKO_GRIDLAYOUT_DEFAULT_WIDGET_LABEL
546+
else:
547+
data_display["label"] = \
548+
WEKO_GRIDLAYOUT_DEFAULT_WIDGET_LABEL
549+
settings["multiLangSetting"] = data_display
550+
settings["name"] = data_display.get('label')
551+
data["widget-settings"] = settings
552+
result["data"][str(widget_item_data.get('widget_id'))] = data
553+
except Exception as e:
554+
result["error"] = str(e)
555+
556+
return result
557+
504558
# TODO: Change to allow specifying which model to retrieve from
505559
@classmethod
506560
def get_widget_preview(cls, repository_id, default_language,

modules/weko-gridlayout/weko_gridlayout/static/js/weko_gridlayout/widget.design.js

Lines changed: 96 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@ const GET_SYSTEM_LANG_URL = '/api/admin/get_system_lang';
2222
const SAVE_WIDGET_LAYOUT_SETTING_URL = "/api/admin/save_widget_layout_setting";
2323
const LOAD_WIDGET_DESIGN_SETTING_URL = "/api/admin/load_widget_design_setting";
2424
const LOAD_WIDGET_DESIGN_PAGE_SETTING_URL = '/api/admin/load_widget_design_page_setting/';
25+
const WIDGET_DESIGN_PREVIEW_URL = '/admin/widgetdesign/preview/';
26+
const GET_WIDGET_DETAIL = '/api/admin/get_widget_item_list'
2527

2628
let windowObjectReference = null;
2729
let previousUrl; /* global variable that will store the
@@ -870,8 +872,12 @@ class ButtonLayout extends React.Component {
870872
"margin-left": "-15px"
871873

872874
};
875+
this.previewStyle = {
876+
"margin-right": "10px"
877+
};
873878
this.handleSave = this.handleSave.bind(this);
874879
this.handleCancel = this.handleCancel.bind(this);
880+
this.handlePreview = this.handlePreview.bind(this);
875881
}
876882

877883
handleSave() {
@@ -913,6 +919,86 @@ class ButtonLayout extends React.Component {
913919
});
914920
}
915921

922+
handlePreview() {
923+
console.log(this.props.repositoryId)
924+
$.ajax({
925+
url: GET_WIDGET_DETAIL,
926+
type: 'GET',
927+
dataType: "json",
928+
contentType: 'application/json',
929+
data: {
930+
repository_id: this.props.repositoryId
931+
},
932+
success: function (res) {
933+
let widgetDetails = res.data
934+
this.serializedData = _.map($('.grid-stack > .grid-stack-item:visible'), function (el) {
935+
el = $(el);
936+
let node = el.data('_gridstack_node');
937+
let id = el.data("id");
938+
let type = el.data("type");
939+
let widget_id = el.data("widget_id");
940+
let created_date = el.data("created_date");
941+
if (!id) {
942+
return;
943+
} else if (MAIN_CONTENT_TYPE === type) {
944+
isHasMainContent = true;
945+
}
946+
947+
let settingWidgetDetail = {}
948+
if (widget_id) {
949+
const widgetDetail = widgetDetails[widget_id]["widget-settings"]
950+
settingWidgetDetail = {
951+
...widgetDetail
952+
}
953+
}
954+
955+
let result = {
956+
x: node.x,
957+
y: node.y,
958+
width: node.width,
959+
height: node.height,
960+
...settingWidgetDetail
961+
};
962+
if (created_date) {
963+
result.created_date = created_date;
964+
}
965+
return result;
966+
}, this);
967+
var widgetDesignData = this.serializedData.filter(function (el) {
968+
return el != null;
969+
});
970+
let repositoryId = document.getElementById("repository-id").value;
971+
let pageListSelectElement = document.getElementById("pages-list-select");
972+
let pageId = "0";
973+
let isMainLayout = true;
974+
if (pageListSelectElement && pageListSelectElement.options) {
975+
pageId = pageListSelectElement.value;
976+
let option = pageListSelectElement.options[pageListSelectElement.selectedIndex];
977+
if (option.dataset) {
978+
isMainLayout = (String(option.dataset.isMainLayout) === "true");
979+
}
980+
}
981+
if (String(repositoryId) === "0") {
982+
alertModal("Please select the Repository.");
983+
return false;
984+
} else if (!widgetDesignData) {
985+
//alert('Please add Widget to Preview panel.');
986+
alertModal("Please add Widget to Preview panel.");
987+
return false;
988+
}
989+
990+
localStorage.setItem("widget_setting_data", JSON.stringify({
991+
"widget-settings": widgetDesignData,
992+
error: ""
993+
}));
994+
window.open(WIDGET_DESIGN_PREVIEW_URL, '_blank');
995+
},
996+
error: function (error) {
997+
console.log(error);
998+
}
999+
});
1000+
}
1001+
9161002
render() {
9171003
return (
9181004
<div className="form-group col-xs-10">
@@ -921,6 +1007,12 @@ class ButtonLayout extends React.Component {
9211007
<span className="glyphicon glyphicon-saved" aria-hidden="true" />
9221008
&nbsp;Save
9231009
</button>
1010+
<button id="preview-widget"
1011+
className="form-group btn btn-success action-button"
1012+
style={this.previewStyle} onClick={this.handlePreview}>
1013+
<span className="glyphicon glyphicon-eye-open" aria-hidden="true" />
1014+
Preview
1015+
</button>
9241016
<button id="clear-grid"
9251017
className="form-group btn btn-info cancel-button"
9261018
onClick={this.handleCancel}>
@@ -1300,7 +1392,7 @@ $(function () {
13001392
});
13011393

13021394
/**
1303-
* Handle disable Save and Cancel button.
1395+
* Handle disable Save and Cancel and Preview button.
13041396
*/
13051397
function disableButton() {
13061398
let repositoryId = document.getElementById("repository-id").value;
@@ -1309,12 +1401,15 @@ function disableButton() {
13091401
}
13101402
let saveGrid = document.getElementById("save-grid");
13111403
let clearGrid = document.getElementById("clear-grid");
1404+
let PreviewWidget = document.getElementById("preview-widget");
13121405
if (String(repositoryId) === "0") {
13131406
saveGrid.setAttribute('disabled', 'disabled');
13141407
clearGrid.setAttribute('disabled', 'disabled');
1408+
PreviewWidget.setAttribute('disabled', 'disabled');
13151409
} else {
13161410
saveGrid.removeAttribute('disabled');
13171411
clearGrid.removeAttribute('disabled');
1412+
PreviewWidget.removeAttribute('disabled');
13181413
}
13191414
}
13201415

0 commit comments

Comments
 (0)