1
0

nightly commit

This commit is contained in:
2021-01-23 18:37:12 +08:00
parent db96ec11a5
commit e4bc3f686f
18 changed files with 473 additions and 119 deletions

View File

@@ -14,6 +14,7 @@ ccn-header-language=Language
ccn-js-failToLogin=Fail to login. Please check your username or password.
ccn-js-failToLogout=Fail to logout due to unknow reason. Consider refreshing page to solve problem.
ccn-js-failToOperate=An operation failed. It may caused by your input wrong data, or system error. Refreshing page may fix system problem. Before refreshing page, please backup all your unsaved data.
ccn-home-desc=<h1 class="title">coconut-leaf</h1><p>A light, self-host calendar system.</p><p>Originally, this app is served for yyc12345 personal use.</p><br /><p>Pull request / issue / translation are welcomed.</p><p>Submit them in our <a href="https://github.com/yyc12345/coconut-leaf">GitHub project</a>.</p><p>This project source code is licensed <a href="https://www.gnu.org/licenses/agpl-3.0.html">AGPL v3</a>.</p>
@@ -21,3 +22,19 @@ ccn-login-form-username=Username
ccn-login-form-password=Password
ccn-login-form-login=Login
ccn-todo-todoList=Todo list
ccn-calendar-jump=Jump
ccn-calendar-today=Today
ccn-calendar-add=Add...
ccn-calendar-scheduleList=Schedule
ccn-calendar-tabcontrol-tabCalendar=Calendar
ccn-calendar-tabcontrol-tabShared=Shared
ccn-calendar-tabcontrol-tabSharing=Sharing
ccn-calendar-week-monday=Monday
ccn-calendar-week-tuesday=Tuesday
ccn-calendar-week-wednesday=Wednesday
ccn-calendar-week-thursday=Thursday
ccn-calendar-week-friday=Friday
ccn-calendar-week-saturday=Saturday
ccn-calendar-week-sunday=Sunday

View File

@@ -14,6 +14,7 @@ ccn-header-language=语言
ccn-js-failToLogin=登陆失败,请检查您的用户名和密码。
ccn-js-failToLogout=由于未知原因,登出失败,请考虑刷新页面解决问题。
ccn-js-failToOperate=一个操作失败了,可能是您输入了错误的参数,又或者是系统错误。刷新页面可能会解决系统错误问题。请在刷新前备份好自己的数据。
ccn-home-desc=<h1 class="title">coconut-leaf</h1><p>一个轻量的自建日历系统</p><p>原本是出于yyc12345的个人使用而制作的。</p><br /><p>欢迎提出Pull request / issue / 翻译</p><p>将他们提交到我们的<a href="https://github.com/yyc12345/coconut-leaf">GitHub项目</a>.</p><p>本工程代码使用<a href="https://www.gnu.org/licenses/agpl-3.0.html">AGPL v3</a>授权。</p>
@@ -21,4 +22,19 @@ ccn-login-form-username=用户名
ccn-login-form-password=密码
ccn-login-form-login=登录
ccn-todo-todoList=待办列表
ccn-calendar-jump=转到
ccn-calendar-today=今天
ccn-calendar-add=添加...
ccn-calendar-scheduleList=日程安排
ccn-calendar-tabcontrol-tabCalendar=日历
ccn-calendar-tabcontrol-tabShared=被共享的
ccn-calendar-tabcontrol-tabSharing=共享给其他人
ccn-calendar-week-monday=星期一
ccn-calendar-week-tuesday=星期二
ccn-calendar-week-wednesday=星期三
ccn-calendar-week-thursday=星期四
ccn-calendar-week-friday=星期五
ccn-calendar-week-saturday=星期六
ccn-calendar-week-sunday=星期日

View File

@@ -49,6 +49,8 @@ function cnn_api_common_login(_username, password) {
}
*/
// ====================================================== common
function cnn_api_common_webLogin(_username, password) {
var gotten_data = undefined;
$.ajax({
@@ -63,7 +65,7 @@ function cnn_api_common_webLogin(_username, password) {
gotten_data = data;
}
});
if (IsResponseOK(gotten_data) && gotten_data['data'] != '') {
if (IsResponseOK(gotten_data)) {
SetApiToken(gotten_data['data']);
return true;
} else return false;
@@ -84,7 +86,7 @@ function cnn_api_common_logout() {
}
});
if (IsResponseOK(gotten_data) && gotten_data['data']) {
if (IsResponseOK(gotten_data)) {
SetApiToken('');
return true;
} return false;
@@ -109,9 +111,106 @@ function cnn_api_common_tokenValid() {
}
});
if (IsResponseOK(gotten_data) && gotten_data['data']) return true;
if (IsResponseOK(gotten_data)) return true;
else {
SetApiToken('');
return false;
}
}
}
// ====================================================== calendar
// ====================================================== collection
// ====================================================== todo
function cnn_api_todo_getFull() {
// return data or undefined
var gotten_data = undefined;
$.ajax({
url: '/api/todo/getFull',
type: "POST",
async: false,
data: {
token: GetApiToken()
},
success: function (data) {
gotten_data = data;
}
});
if (IsResponseOK(gotten_data)) return gotten_data['data'];
else return undefined;
}
function cnn_api_todo_add() {
// return data or undefined
var gotten_data = undefined;
$.ajax({
url: '/api/todo/add',
type: "POST",
async: false,
data: {
token: GetApiToken()
},
success: function (data) {
gotten_data = data;
}
});
if (IsResponseOK(gotten_data)) return gotten_data['data'];
else return undefined;
}
function cnn_api_todo_update(_uuid, _data, _lastChange) {
// return data or undefined
var gotten_data = undefined;
$.ajax({
url: '/api/todo/update',
type: "POST",
async: false,
data: {
token: GetApiToken(),
uuid: _uuid,
data: _data,
lastChange: _lastChange
},
success: function (data) {
gotten_data = data;
}
});
if (IsResponseOK(gotten_data)) return gotten_data['data'];
else return undefined;
}
function cnn_api_todo_delete(_uuid, _lastChange) {
// return true or false
var gotten_data = undefined;
$.ajax({
url: '/api/todo/delete',
type: "POST",
async: false,
data: {
token: GetApiToken(),
uuid: _uuid,
lastChange: _lastChange
},
success: function (data) {
gotten_data = data;
}
});
return IsResponseOK(gotten_data);
}
// ====================================================== admin

View File

@@ -34,7 +34,7 @@ function ccn_i18n_ApplyLanguage() {
language: ccn_i18n_currentLanguage,
callback: function() {
//set usual block
var cache = $(".ccn-i18n");
var cache = $("[i18n-name]");
cache.each(function() {
$(this).html($.i18n.prop($(this).attr('i18n-name')));
});

View File

@@ -8,6 +8,18 @@ $(document).ready(function() {
// process calendar it self
ccn_calendar_LoadCalendarBody();
// bind tab control switcher and set current tab
$("#tabcontrol-tab-1-1").click(function(){
ccn_tabcontrol_SwitchTab(1, 1);
});
$("#tabcontrol-tab-1-2").click(function(){
ccn_tabcontrol_SwitchTab(1, 2);
});
$("#tabcontrol-tab-1-3").click(function(){
ccn_tabcontrol_SwitchTab(1, 3);
});
ccn_tabcontrol_SwitchTab(1, 1);
// apply i18n
ccn_i18n_ApplyLanguage();
});

View File

@@ -6,13 +6,13 @@ $(document).ready(function() {
cnn_headerNav_LoggedRefresh();
// bind login event
$("#ccn-login-form-login").click(StartLogin);
$("#ccn-login-form-login").click(ccn_login_startLogin);
// apply i18n
ccn_i18n_ApplyLanguage();
});
function StartLogin() {
function ccn_login_startLogin() {
// disable all ui first
$("#ccn-login-form-login").attr("disabled",true);
$("#ccn-login-form-username").attr("disabled",true);

View File

@@ -0,0 +1,202 @@
var ccn_todo_todoListCache = [];
$(document).ready(function() {
// nav process
ccn_pages_currentPage = ccn_pages_enumPages.login;
cnn_headerNav_Insert();
cnn_headerNav_BindEvents();
cnn_headerNav_LoggedRefresh();
// refresh once
ccn_todo_Refresh();
// bind event
$("#ccn-todo-btnAdd").click(ccn_todo_Add);
$("#ccn-todo-btnRefresh").click(ccn_todo_Refresh);
// apply i18n
ccn_i18n_ApplyLanguage();
});
function ccn_todo_RefreshCacheList() {
// clean list cache first
ccn_todo_todoListCache = new Array();
var result = cnn_api_todo_getFull();
if(typeof(result) != 'undefined') {
for(var index in result) {
ccn_todo_todoListCache[result[index][0]] = result[index];
}
}
}
function ccn_todo_RenderCacheList() {
// clean list first
$("#ccn-todo-todoList").empty();
var renderdata = {
uuid: undefined,
data: undefined
};
var templates = undefined;
$.ajax({
url: $("#jsrender-tmpl-todoItem").attr('src'),
type: "GET",
async: false,
success: function (data) {
templates = $.templates(data);
}
});
var listDOM = $("#ccn-todo-todoList");
for(var index in ccn_todo_todoListCache) {
// update render data
var item = ccn_todo_todoListCache[index];
renderdata.uuid = item[0];
renderdata.data = item[2];
// render
listDOM.append(templates.render(renderdata));
// set mode
var uuid = renderdata.uuid;
ccn_todo_ChangeDisplayMode(uuid, false);
// bind event
$("#ccn-todo-todoItem-btnEdit-" + uuid).click(ccn_todo_ItemEdit);
$("#ccn-todo-todoItem-btnDelete-" + uuid).click(ccn_todo_ItemDelete);
$("#ccn-todo-todoItem-btnUpdate-" + uuid).click(ccn_todo_ItemUpdate);
$("#ccn-todo-todoItem-btnCancelUpdate-" + uuid).click(ccn_todo_ItemCancelUpdate);
}
}
function ccn_todo_ChangeDisplayMode(uuid, isEdit) {
if(isEdit) {
// 4 buttons
$("#ccn-todo-todoItem-btnEdit-" + uuid).hide();
$("#ccn-todo-todoItem-btnDelete-" + uuid).hide();
$("#ccn-todo-todoItem-btnUpdate-" + uuid).show();
$("#ccn-todo-todoItem-btnCancelUpdate-" + uuid).show();
// 2 elements
$("#ccn-todo-todoItem-p-" + uuid).hide();
$("#ccn-todo-todoItem-textarea-" + uuid).show();
} else {
$("#ccn-todo-todoItem-btnEdit-" + uuid).show();
$("#ccn-todo-todoItem-btnDelete-" + uuid).show();
$("#ccn-todo-todoItem-btnUpdate-" + uuid).hide();
$("#ccn-todo-todoItem-btnCancelUpdate-" + uuid).hide();
$("#ccn-todo-todoItem-p-" + uuid).show();
$("#ccn-todo-todoItem-textarea-" + uuid).hide();
}
}
function ccn_todo_Refresh() {
// refresh and render once
ccn_todo_RefreshCacheList();
ccn_todo_RenderCacheList();
}
function ccn_todo_Add() {
var result = cnn_api_todo_add();
if (typeof(result) == 'undefined') {
// fail
alert($.i18n.prop("ccn-js-failToOperate"));
} else {
// add into cache
ccn_todo_todoListCache[result[0]] = result;
// render
var templates = undefined;
$.ajax({
url: $("#jsrender-tmpl-todoItem").attr('src'),
type: "GET",
async: false,
success: function (data) {
templates = $.templates(data);
}
});
// render
var listDOM = $("#ccn-todo-todoList");
listDOM.append(templates.render({
uuid: result[0],
data: result[2]
}));
// set mode
var uuid = result[0];
ccn_todo_ChangeDisplayMode(uuid, false);
// bind event
$("#ccn-todo-todoItem-btnEdit-" + uuid).click(ccn_todo_ItemEdit);
$("#ccn-todo-todoItem-btnDelete-" + uuid).click(ccn_todo_ItemDelete);
$("#ccn-todo-todoItem-btnUpdate-" + uuid).click(ccn_todo_ItemUpdate);
$("#ccn-todo-todoItem-btnCancelUpdate-" + uuid).click(ccn_todo_ItemCancelUpdate);
}
}
function ccn_todo_ItemEdit() {
var uuid = $(this).attr("uuid");
// copy current data to textarea
$("#ccn-todo-todoItem-textarea-" + uuid).val(
$("#ccn-todo-todoItem-p-" + uuid).text()
);
// switch to edit mode
ccn_todo_ChangeDisplayMode(uuid, true);
}
function ccn_todo_ItemDelete() {
var uuid = $(this).attr("uuid");
var result = cnn_api_todo_delete(
uuid,
ccn_todo_todoListCache[uuid][3]
);
if(typeof(result) == 'undefined') {
// fail
alert($.i18n.prop("ccn-js-failToOperate"));
} else {
// remove body
$("#ccn-todo-todoItem-" + uuid).remove();
}
}
function ccn_todo_ItemUpdate() {
var uuid = $(this).attr("uuid");
var newData = $("#ccn-todo-todoItem-textarea-" + uuid).val();
var result = cnn_api_todo_update(
uuid,
newData,
ccn_todo_todoListCache[uuid][3]
);
if (typeof(result) == 'undefined') {
// fail
alert($.i18n.prop("ccn-js-failToOperate"));
} else {
// safely update data & lastChanged and control
ccn_todo_todoListCache[uuid][2] = newData;
ccn_todo_todoListCache[uuid][3] = result;
$("#ccn-todo-todoItem-p-" + uuid).text(newData);
// switch to normal mode
ccn_todo_ChangeDisplayMode(uuid, false);
}
}
function ccn_todo_ItemCancelUpdate() {
var uuid = $(this).attr("uuid");
// clean data
$("#ccn-todo-todoItem-textarea-" + uuid).val("");
// switch to normal mode
ccn_todo_ChangeDisplayMode(uuid, false);
}

View File

@@ -0,0 +1,10 @@
// all args are based on 1
function ccn_tabcontrol_SwitchTab(tabcontrolGroup, targetTabIndex) {
// close all panel and tab
$(".tabcontrol-tab-" + tabcontrolGroup).removeClass("is-active");
$(".tabcontrol-panel-" + tabcontrolGroup).hide();
// show specific
$("#tabcontrol-tab-" + tabcontrolGroup + "-" + targetTabIndex).addClass("is-active");
$("#tabcontrol-panel-" + tabcontrolGroup + "-" + targetTabIndex).show();
}

View File

@@ -1,3 +1,4 @@
/*
function ComputPasswordWithSalt(password, salt) {
return ComputeSHA256(ComputeSHA256(password) + salt.toString());
}
@@ -13,6 +14,7 @@ function ComputeSHA256(strl) {
var hashHex = hashArray.map(b => ('00' + b.toString(16)).slice(-2)).join('');
return hashHex.toLowerCase();
}
*/
function IsResponseOK(data) {
if (typeof(data) == 'undefined') {

View File

@@ -14,22 +14,22 @@
<div id="navbarBasicExample" class="navbar-menu">
<div class="navbar-start">
<a i18n-name="ccn-header-nav-home" id="cnn-header-nav-home" class="navbar-item ccn-i18n" href="/web/home"></a>
<a i18n-name="ccn-header-nav-calendar" id="cnn-header-nav-calendar" class="navbar-item ccn-i18n" href="/web/calendar"></a>
<a i18n-name="ccn-header-nav-todo" id="cnn-header-nav-todo" class="navbar-item ccn-i18n" href="/web/todo"></a>
<a i18n-name="ccn-header-nav-admin" id="cnn-header-nav-admin" class="navbar-item ccn-i18n" href="/web/admin"></a>
<a i18n-name="ccn-header-nav-home" id="cnn-header-nav-home" class="navbar-item" href="/web/home"></a>
<a i18n-name="ccn-header-nav-calendar" id="cnn-header-nav-calendar" class="navbar-item" href="/web/calendar"></a>
<a i18n-name="ccn-header-nav-todo" id="cnn-header-nav-todo" class="navbar-item" href="/web/todo"></a>
<a i18n-name="ccn-header-nav-admin" id="cnn-header-nav-admin" class="navbar-item" href="/web/admin"></a>
</div>
<div class="navbar-end">
<p id="cnn-header-user-login" class="navbar-item">
<a class="button is-primary ccn-i18n" i18n-name="ccn-header-user-login" href="/web/login"></a>
<a class="button is-primary" i18n-name="ccn-header-user-login" href="/web/login"></a>
</p>
<p id="cnn-header-user-logout" class="navbar-item">
<a class="button is-primary ccn-i18n" i18n-name="ccn-header-user-logout"></a>
<a class="button is-primary" i18n-name="ccn-header-user-logout"></a>
</p>
<div class="navbar-item has-dropdown is-hoverable">
<a class="navbar-link ccn-i18n" i18n-name="ccn-header-language"></a>
<a class="navbar-link" i18n-name="ccn-header-language"></a>
<div id="cnn-header-language" class="navbar-dropdown">
<a language="en-US" class="navbar-item">English</a>

View File

@@ -1,27 +1,20 @@
<div class="todo-item card">
<div id="ccn-todo-todoItem-{{:uuid}}" class="todo-item card">
<div class="todo-item-words">
<p>this is a
namewwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwww
</p>
<p id="ccn-todo-todoItem-p-{{:uuid}}">{{>data}}</p>
<textarea id="ccn-todo-todoItem-textarea-{{:uuid}}" class="textarea"></textarea>
</div>
<div class="todo-item-icon control">
<div id="ccn-todo-todoItem-btnEdit-{{:uuid}}" uuid="{{:uuid}}" class="todo-item-icon control">
<button class="button"><span class="icon is-small"><i class="fas fa-pen"></i></span></button>
</div>
<div class="todo-item-icon control">
<div id="ccn-todo-todoItem-btnDelete-{{:uuid}}" uuid="{{:uuid}}" class="todo-item-icon control">
<button class="button"><span class="icon is-small"><i class="fas fa-trash"></i></button>
</div>
</div>
<div class="todo-item card">
<div class="todo-item-words control">
<textarea class="textarea"></textarea>
</div>
<div class="todo-item-icon control">
<div id="ccn-todo-todoItem-btnUpdate-{{:uuid}}" uuid="{{:uuid}}" class="todo-item-icon control">
<button class="button"><span class="icon is-small"><i class="fas fa-check"></i></span></button>
</div>
<div class="todo-item-icon control">
<div id="ccn-todo-todoItem-btnCancelUpdate-{{:uuid}}" uuid="{{:uuid}}" class="todo-item-icon control">
<button class="button"><span class="icon is-small"><i class="fas fa-times"></i></button>
</div>
</div>