Skip to content

Commit dffbed7

Browse files
committed
Merge remote-tracking branch 'origin/main'
2 parents 87075e9 + 9468bd5 commit dffbed7

File tree

8 files changed

+167
-4
lines changed

8 files changed

+167
-4
lines changed

Data/users.db

0 Bytes
Binary file not shown.

TightWiki.Engine.Implementation/Handlers/ScopeFunctionHandler.cs

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,9 @@ public FunctionPrototypeCollection Prototypes
5959
_collection.Add("Table (Boolean hasBorder='true', Boolean isFirstRowHeader='true')");
6060
_collection.Add("StripedTable (Boolean hasBorder='true', Boolean isFirstRowHeader='true')");
6161
_collection.Add("DefineSnippet (String name)");
62+
_collection.Add("Blockquote (String styleName['default','start','center','end']='default', String caption='')");
63+
_collection.Add("Figure (String styleName['default','start','center','end']='default', String caption='')");
64+
6265
}
6366

6467
return _collection;
@@ -380,9 +383,51 @@ public HandlerResult Handle(ITightEngineState state, FunctionCall function, stri
380383
html.Append("</div>");
381384
html.Append("</div>");
382385
return new HandlerResult(html.ToString());
386+
}
387+
388+
//------------------------------------------------------------------------------------------------------------------------------
389+
case "blockquote":
390+
{
391+
var html = new StringBuilder();
392+
393+
string caption = function.Parameters.Get<string>("caption");
394+
var style = AlignStyle.GetStyle(function.Parameters.Get("styleName", "default"));
395+
396+
html.Append($"<figure class=\"{style.Style}\">");
397+
html.Append($"<blockquote class=\"blockquote\">{scopeBody}</blockquote >");
398+
399+
if (string.IsNullOrEmpty(caption) == false)
400+
{
401+
html.Append("<figcaption class=\"blockquote-footer\">");
402+
html.Append($"{caption}");
403+
html.Append("</figcaption>");
404+
}
405+
html.Append("</figure>");
406+
return new HandlerResult(html.ToString());
407+
}
408+
409+
//------------------------------------------------------------------------------------------------------------------------------
410+
case "figure":
411+
{
412+
var html = new StringBuilder();
413+
414+
string caption = function.Parameters.Get<string>("caption");
415+
var style = AlignStyle.GetStyle(function.Parameters.Get("styleName", "default"));
383416

417+
html.Append($"<figure class=\"figure\">");
418+
html.Append($"{scopeBody}");
419+
420+
if (string.IsNullOrEmpty(caption) == false)
421+
{
422+
html.Append($"<figcaption class=\"figure-caption {style.Style}\">");
423+
html.Append($"{caption}");
424+
html.Append("</figcaption>");
425+
}
426+
html.Append("</figure>");
427+
return new HandlerResult(html.ToString());
384428
}
385429

430+
386431
}
387432

388433
return new HandlerResult() { Instructions = [HandlerResultInstruction.Skip] };

TightWiki.Engine.Implementation/Handlers/StandardFunctionHandler.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,7 @@ public FunctionPrototypeCollection Prototypes
7676
_collection.Add("Revisions (String styleName['Full','List']='Full', Integer pageSize='5', Boolean pageSelector='true', String pageName=null)");
7777
_collection.Add("Attachments (String styleName['Full','List']='Full', Integer pageSize='5', Boolean pageSelector='true', String pageName=null)");
7878
_collection.Add("Title ()");
79+
_collection.Add("Description ()");
7980
_collection.Add("Navigation ()");
8081
_collection.Add("Name ()");
8182
_collection.Add("SiteName ()");
@@ -1064,6 +1065,13 @@ public HandlerResult Handle(ITightEngineState state, FunctionCall function, stri
10641065
return new HandlerResult($"<h1>{state.Page.Title}</h1>");
10651066
}
10661067

1068+
//------------------------------------------------------------------------------------------------------------------------------
1069+
//Displays the description of the current page.
1070+
case "description":
1071+
{
1072+
return new HandlerResult($"<h1>{state.Page.Description}</h1>");
1073+
}
1074+
10671075
//------------------------------------------------------------------------------------------------------------------------------
10681076
//Displays the namespace of the current page.
10691077
case "namespace":
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
namespace TightWiki.Engine.Implementation.Utility
2+
{
3+
public class AlignStyle
4+
{
5+
public string Style { get; set; } = String.Empty;
6+
7+
public AlignStyle(string style)
8+
{
9+
Style = style;
10+
}
11+
12+
public AlignStyle()
13+
{
14+
}
15+
16+
public static readonly Dictionary<string, AlignStyle> AlignStyles = new(StringComparer.OrdinalIgnoreCase)
17+
{
18+
{ "start", new AlignStyle("text-start") },
19+
{ "center", new AlignStyle("text-center") },
20+
{ "end", new AlignStyle("text-end") },
21+
};
22+
23+
24+
public static AlignStyle GetStyle(string style)
25+
{
26+
if (AlignStyles.TryGetValue(style, out var html))
27+
{
28+
return html;
29+
}
30+
31+
return new AlignStyle();
32+
}
33+
34+
}
35+
}

TightWiki/Controllers/PageController.cs

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
using NTDLS.Helpers;
55
using SixLabors.ImageSharp;
66
using System.Text;
7+
using System.Xml.Linq;
8+
using System.Xml.Serialization;
79
using TightWiki.Caching;
810
using TightWiki.Engine;
911
using TightWiki.Engine.Implementation.Utility;
@@ -33,6 +35,15 @@ public ContentResult RobotsTxt()
3335
return Content(sb.ToString(), "text/plain", Encoding.UTF8);
3436
}
3537

38+
39+
[Authorize]
40+
[Route("/ping")]
41+
public JsonResult Ping()
42+
{
43+
return Json(new { now = DateTime.UtcNow });
44+
}
45+
46+
3647
#region Display.
3748

3849
/// <summary>
@@ -830,5 +841,30 @@ public ActionResult Binary(string givenPageNavigation, string givenFileNavigatio
830841
}
831842

832843
#endregion
844+
845+
#region Export/import
846+
847+
[Authorize]
848+
[HttpGet("{givenCanonical}/Export")]
849+
public IActionResult Export(string givenCanonical)
850+
{
851+
SessionState.RequireViewPermission();
852+
853+
var model = new PageDisplayViewModel();
854+
var navigation = new NamespaceNavigation(givenCanonical);
855+
856+
var page = PageRepository.GetPageRevisionByNavigation(navigation.Canonical);
857+
if (page == null)
858+
return NotFound();
859+
860+
var sr = new StringWriter();
861+
var writer = new System.Xml.XmlTextWriter(sr);
862+
var serializer = new XmlSerializer(typeof(Page));
863+
serializer.Serialize(writer, page);
864+
865+
return File(Encoding.UTF8.GetBytes(sr.ToString()), "text/xml", $"{givenCanonical}.xml");
866+
}
867+
868+
#endregion
833869
}
834870
}

TightWiki/Views/Page/Edit.cshtml

Lines changed: 37 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,32 @@
130130
uploadStatus.innerHTML = `<p>Unexpected Error: ${error.message}</p>`;
131131
});
132132
}
133+
134+
setInterval(ping, 60000);
133135
});
136+
137+
138+
139+
function ping() {
140+
const spans = document.querySelectorAll('.badge.text-bg-danger');
141+
fetch('@Url.Action("Ping", "Page")?r=' + Math.random(), { method: 'GET' })
142+
.then(response => response.json())
143+
.then(result => {
144+
if (result.now) {
145+
spans[0].classList.add("invisible");
146+
spans[1].classList.add("invisible");
147+
}
148+
else {
149+
spans[0].classList.remove("invisible");
150+
spans[1].classList.remove("invisible");
151+
}
152+
})
153+
.catch(error => {
154+
spans[0].classList.remove("invisible");
155+
spans[1].classList.remove("invisible");
156+
});
157+
}
158+
134159
</script>
135160

136161
<div class="bodyDiv">
@@ -143,7 +168,12 @@
143168

144169
<div class="form-group">
145170
<button type="submit" class="btn btn-primary rounded-0">Save</button>
146-
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation" target="_blank" rel="noopener" class="btn btn-success rounded-0" role="button">View</a>
171+
@if (Model?.Id > 0 && sessionState.CanView == true)
172+
{
173+
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation" target="_blank" rel="noopener" class="btn btn-success rounded-0" role="button">View</a>
174+
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation/Export" target="_blank" rel="noopener" class="btn btn-secondary rounded-0" role="button">Export</a>
175+
}
176+
<span class="badge text-bg-danger invisible">unauthorized</span>
147177
</div>
148178
<br />
149179
<strong>@Html.LabelFor(x => x.Name)</strong>
@@ -185,7 +215,12 @@
185215

186216
<div class="form-group">
187217
<button type="submit" class="btn btn-primary rounded-0">Save</button>
188-
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation" target="_blank" rel="noopener" class="btn btn-success rounded-0" role="button">View</a>
218+
@if (Model?.Id > 0 && sessionState.CanView == true)
219+
{
220+
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation" target="_blank" rel="noopener" class="btn btn-success rounded-0" role="button">View</a>
221+
<a href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation/Export" target="_blank" rel="noopener" class="btn btn-secondary rounded-0" role="button">Export</a>
222+
}
223+
<span class="badge text-bg-danger invisible">unauthorized</span>
189224
</div>
190225
}
191226
</div>

TightWiki/Views/Shared/_Layout.cshtml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,10 @@
140140
{
141141
<a class="dropdown-item text-dark" href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation">View</a>
142142
}
143+
if (sessionState.CanView == true)
144+
{
145+
<a class="dropdown-item text-dark" href="@GlobalConfiguration.BasePath/@sessionState.PageNavigation/Export">Export</a>
146+
}
143147
}
144148
</div>
145149
</li>

TightWiki/wwwroot/codemirror/mode/tightwiki/tightwiki.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,9 +27,9 @@
2727
"use strict";
2828

2929
CodeMirror.defineMode("tightwiki", function () {
30-
var functions = ["##systememojicategorylist", "##systememojilist", "##set", "##seq", "##get", "##color", "##searchlist", "##taglist", "##searchcloud", "##tagglossary", "##recentlymodified", "##textglossary", "##tagcloud", "##image", "##file", "##related", "##tags", "##editlink", "##inject", "##include", "##br", "##hr", "##revisions", "##attachments", "##toc", "##title", "##navigation", "##name", "##created", "##lastmodified", "##sitename", "##appversion", "##profileglossary", "##profilelist", "##namespaceglossary", "##namespacelist","##namespace", "##snippet"],
30+
var functions = ["##systememojicategorylist", "##systememojilist", "##set", "##seq", "##get", "##color", "##searchlist", "##taglist", "##searchcloud", "##tagglossary", "##recentlymodified", "##textglossary", "##tagcloud", "##image", "##file", "##related", "##tags", "##editlink", "##inject", "##include", "##br", "##hr", "##revisions", "##attachments", "##toc", "##title", "##navigation", "##name", "##created", "##lastmodified", "##sitename", "##appversion", "##profileglossary", "##profilelist", "##namespaceglossary", "##namespacelist", "##namespace", "##snippet", "##description"],
3131
instructions = ["@@protect", "@@hidefooterlastmodified", "@@tags", "@@title", "@@hidefootercomments", "@@nocache", "@@draft", "@@review", "@@deprecate", "@@include", "@@template"],
32-
scopes = ["bullets", "alert", "background", "collapse", "callout", "code", "foreground", "jumbotron", "card", "table", "stripedtable", "definesnippet", "order"];
32+
scopes = ["bullets", "alert", "background", "collapse", "callout", "code", "foreground", "jumbotron", "card", "table", "stripedtable", "definesnippet", "order", "blockquote", "figure"];
3333

3434
function basicToken(stream, state) {
3535

0 commit comments

Comments
 (0)