BUGFIX Suche

This commit is contained in:
Simon Martens
2024-01-26 10:04:59 +01:00
parent cf1b45816e
commit 60a5aea613
5 changed files with 199 additions and 212 deletions

View File

@@ -1,17 +1,17 @@
# Building and preparation # Building and preparation
## Prep ## Prep
To build the project install nodejs > 16.5 LTS. Install npm > 8.10.0. After that, do an `npm install` in the project directory to install the necessary dependencies. Nodejs is used for css scaffolding, this project uses `postcss`, with the `tailwindcss` CSS framework as a postcss plugin to only include used classes. Also, the `postcss-import` postcss-plugin is used to allow for compartmentalization of css files and the import statement to merge those files together (be careful of the order of commands in `postcss.config.js`!). `autoprefixer` and `css-nano` plugins are recommended at least for production builds since they provide cross-browser-compatibility and minification of file size for css files. To build the project install nodejs > 16.5 LTS. Install npm > 8.10.0. After that, do an `npm install` in the project directory to install the necessary dependencies. Nodejs is used for css and javascript scaffolding, this project uses `vite` and `postcss`, with the `tailwindcss` CSS framework as a postcss plugin to only include used classes (be careful of the order of commands in `postcss.config.js`!). `autoprefixer` and `css-nano` plugins are recommended at least for production builds since they provide cross-browser-compatibility and minification of file size for css files.
Dotnet 6.0.300 is currently used. To build the project, do a `dotnet restore` and collect the `Microsoft.FeatureManagement.AspNetCore` nuget-package which is used to enable feauture-flags in `appsettings.json`. Some routes, such as the admin area of the project will only be mapped if certain flags are present and set to true. Dotnet 6 is currently used. To build the project, do a `dotnet restore` and collect the `Microsoft.FeatureManagement.AspNetCore` nuget-package which is used to enable feauture-flags in `appsettings.json`. Some routes, such as the admin area of the project will only be mapped if certain flags are present and set to true.
Also, this project requires two other projects `HaDocumentV6` (for reading in the file into convenient to use models) and `HaXMLReader` (for forward parsing elements such as letters, comments, traditions and marginals in an HTML transform). They have no dependencies (apart from each other and `.NET 6`) and are build and linked at build time automatically. Also, this project requires two other projects `HaDocumentV6` (for reading in the file into convenient to use models) and `HaXMLReader` (for forward parsing elements such as letters, comments, traditions and marginals in an HTML transform). They have no dependencies (apart from each other and `.NET 6`) and are build and linked at build time automatically.
## Building the project ## Building the project
`dotnet build Tailwind.csproj` or `npm run css_build` `npm run build`
to build the necessary `output.css`-File. to build the necessary `wwwroot/dist/styles.css` & `wwwroot/dist/scripts.js`-Files.
`dotnet build HaWeb.csproj` `dotnet build HaWeb.csproj`
@@ -19,7 +19,7 @@ to build the Website. Please do consider the order of these commands.
Don't forget to place a valid `Hamann.xml`-File in the root of the build to provide a starting and fallback XML-file. Don't forget to place a valid `Hamann.xml`-File in the root of the build to provide a starting and fallback XML-file.
Note that nodejs is used only as a build tool for css (and possibly in the future javascript) processing. To host the website there is no node needed. Note that nodejs is used only as a build tool for css and javascript. To host the website there is no node needed.
## Development tools ## Development tools
@@ -27,9 +27,9 @@ Set the `DOTNET_ENVIRONMENT` variable to `Development`. Run
`dotnet watch run` and `dotnet watch run` and
`npm run watch` or `npm run dev` or
`bun run watch` `bun run dev`
in seperate terminals to watch for specific file changes in .css / .js / .cshtml / .json or .cs files and to rebuild the css-Files and the app automatically on change. in seperate terminals to watch for specific file changes in .css / .js / .cshtml / .json or .cs files and to rebuild the css-Files and the app automatically on change.
@@ -37,8 +37,7 @@ There is a chance you need to set the Environment Variable to 'Development' in W
Recommended vscode plugins include the XML Tools, c#, Tailwind CSS IntelliSense & TODO Tree. Recommended vscode plugins include the XML Tools, c#, Tailwind CSS IntelliSense & TODO Tree.
## Release ## Releas
For a Linux server run: For a Linux server run:
@@ -52,91 +51,4 @@ In the appropriate settings (set the `DOTNET_ENVIRONMENT` variable on the server
- RepositoryBranch - RepositoryBranch
- RepositoryURL - RepositoryURL
Absolute paths, sadly, are reqired. Create Folders if neccessary. Reading rights are required for `HamannFileStoreLinux` (to save the state). The `BareRepositoryPath` usually is the `.git` Folder inside the Repo, where the Server gets the latest commit information from `refs/heads/<Branch-Name>`. To sync either you set up a git server and set the server as remote of the repository to push. Or use git webhooks to pull on pushes. Absolute paths, sadly, are reqired. Create Folders if neccessary. Writing rights are required for `HamannFileStoreLinux` (to save the state). The `BareRepositoryPath` usually is the `.git` Folder inside the Repo, where the Server gets the latest commit information from `refs/heads/<Branch-Name>`. To sync either you set up a git server and set the server as remote of the repository to push. Or use git webhooks to pull on pushes.
## Redesign der Hamann-Vebseite, drittes Update
Veränderungenen in der Funktionalität für den Benutzer
- Behutsames Redesign der Webseite:
- Schrift wird minimal größer auf großen Bildschirmen
- Redesign der Marginalspalte, sodass keine Überschneidungen vorkommen, gut für screenreader
- Leichtes Redesign der Zusatzinformationen für einen Brief (Tradition, Edits) an etwas prominenterer Stelle
- Anpassung der Webseite an Mobilgeräte und Tablets
- Suche im Brieftext wird gefixt
- Seite wird zugänglich für Menschen mit eingeschränktem Sehvermögen / Screenreadern
- Bibellinks in Bibelkommentaren
- Verbesserte Ladezeiten
- Startseite für die Briefausgebe / Werkausgabe. Unterschiedliche Menüs für die Ausgaben
- URL für die Register hat sich geändert, bleibt aber weiter unter `/Supplementa/` zugängig.
- Ebenso alle anderen URLs für die Briefausgabe
- Anzeige Briefe beim Namen (?)
- GeoCities und Personen-Verweise (?)
Veränderungen in der Funktionalität für die Redakteure
- Online-Syntaxcheck für XML-Dateien (Noch nicht implementiert)
- Online-Cross-Dateien-Check (bsp. verweist jede Marginalie auf eine existierende Zeile) (Noch nicht implementiert)
- Erstellung einer HAMANN.xml-Datei, hochladen der HAMANN.xml-Datei auf die Plattform
Veränderungen im Code
- Anpassung des Codes an .NET 6
- Umzug nach CSS Framework Tailwind
- Code ist aufgeräumt und sortiert
- Leichtere Anpassungen an zukünftige Bedürfnisse (Wartungszeiten minimieren)
- Auslagerungen einzelner Einstellungen in Einstellungsdateien
- Code wird open source zugänglich
Ästhetisch unzufriedenstellend, aber funktional:
B TODO pills are not mobile friendly (hover / click), Pills allgemein Ästhetik
D TODO High Contrast Mode manchmal komisch
D TODO Kein High Contrast Mode für den Upload
D TODO High Contrast Mode: Kursiv und ausgegraut (Herausgeberanmerkungen) schwer sichtbar
D TODO 400: Traditions nicht genug Abstand
Technische Details:
D TODO Move ILibrary -> neuer Parser
C TODO Syntax-Check
A TODO Fußnoten in Editionsgeschichte als Marginalkommentare
(Am Besten) Vor dem release:
A TODO Kopieren von Text ermöglichen, mit SPAN arbeiten
B TODO Suchergebnisse beschränken
B TODO Mobile Menüs bei der Seitennavigation (Jahrszahlen, Buchstabenindex usw)
C TODO Traditions durchsuchen
Bugs für Janina/Luca:
tabellen ok, ausser 939
KOmmentare verschobem 202 Anhang
Known Bugs:
- click event does not work in iOS
- rerender marginals on tab switch
GIT-UMBAU:
- OPUS-Check briefe
- SYNTAX-Check
- ILIB
(- Searchables)
Start: kein background service
Datei vom Admin-Panel laden: kein bacckground service
Datei ändert sich: background service + reload call on all clients
Konfiguration ändert sich: kein background service
BACKGROUND SERVICE:
- FileWatch
- XMLInteractionService.Collect(List<IFileInfo>)
- XMLInteractionService.TryCreate()
- XMLFileProvider.SaveHamannFile(XElement element, string basefilepath, ModelStateDictionary? ModelState)
BACKGROUND SERVICE WITH JSON OUTPUT:
- XMLTestService.Test(XMLInteractionService)
KEIN BACKGROUND SERVICE:
- HaDocuemntWrapper.SetLibrary(IFileInfo? file, XDocument? doc, ModelStateDictionary? ModelState = null)
- XMLInteractionService.CreateSearchables(XDocument document)
TASKS:
- Syntax Errors nicht mehr im FileModel loggen
- State für Collect()
- State für TryCreate()

25
HaWeb/Stuff.md Normal file
View File

@@ -0,0 +1,25 @@
Ästhetisch unzufriedenstellend, aber funktional:
B TODO pills are not mobile friendly (hover / click), Pills allgemein Ästhetik
D TODO High Contrast Mode manchmal komisch
D TODO Kein High Contrast Mode für den Upload
D TODO High Contrast Mode: Kursiv und ausgegraut (Herausgeberanmerkungen) schwer sichtbar
D TODO 400: Traditions nicht genug Abstand
Technische Details:
D TODO Move ILibrary -> neuer Parser
C TODO Syntax-Check
A TODO Fußnoten in Editionsgeschichte als Marginalkommentare
(Am Besten) Vor dem release:
A TODO Kopieren von Text ermöglichen, mit SPAN arbeiten
B TODO Suchergebnisse beschränken
B TODO Mobile Menüs bei der Seitennavigation (Jahrszahlen, Buchstabenindex usw)
C TODO Traditions durchsuchen
Bugs für Janina/Luca:
tabellen ok, ausser 939
KOmmentare verschobem 202 Anhang
Known Bugs:
- click event does not work in iOS
- rerender marginals on tab switch

View File

@@ -10,148 +10,198 @@
<div class="ha-searchhead"> <div class="ha-searchhead">
<h1>Volltextsuche</h1> <h1>Volltextsuche</h1>
<div class="ha-searchfilterinfo hyphenate"> <div class="ha-searchfilterinfo hyphenate">
Die Volltextsuche kann Brieftexte, Stellenkommentare, Forschungsbibliographie und Registereinträge über Seiten- und Zeilengrenzen hinweg durchsuchen. Angezeigt werden dabei exakte Übereinstimmungen mit dem Suchbegriff. Von dieser Regel ausgenommen sind Abweichungen in der Groß- und Kleinschreibung. Die Volltextsuche kann Brieftexte, Stellenkommentare, Forschungsbibliographie und Registereinträge über
Seiten- und Zeilengrenzen hinweg durchsuchen. Angezeigt werden dabei exakte Übereinstimmungen mit dem
Suchbegriff. Von dieser Regel ausgenommen sind Abweichungen in der Groß- und Kleinschreibung.
</div> </div>
<div class="ha-searchfilter"> <div class="ha-searchfilter">
@if (Model.ActiveSearch != null) { @if (Model.ActiveSearch != null)
<div class="ha-activefilterinfo"> {
@if (Model.SearchType == SearchType.Letters) { <div class="ha-activefilterinfo">
<span><span class="">Briefe</span>@if(Model.IncludeComments == true) {<span> und Stellenkommentare</span>}, die »@Model.ActiveSearch« enthalten.&emsp;</span><br> @if (Model.SearchType == SearchType.Letters)
<a class="ha-reversefilter" asp-controller="Index" asp-action="Index">← Briefübersicht</a> {
} <span><span class="">Briefe</span>@if (Model.IncludeComments == true)
@if (Model.SearchType == SearchType.Register) { {
<span><span class="">Registereinträge</span>, die »@Model.ActiveSearch« enthalten.&emsp;</span><br> <span> und
<a class="ha-reversefilter" asp-controller="Register" asp-action="Allgemein">← Register</a><span></span> Stellenkommentare</span>
} }, die »@Model.ActiveSearch« enthalten.&emsp;</span>
@if (Model.SearchType == SearchType.Science) {
<span><span class="">Bibliografische Einträge</span>, die »@Model.ActiveSearch« enthalten.&emsp;</span><br>
<a class="ha-reversefilter" asp-controller="Register" asp-action="Forschung">← Forschungsbibliographie</a><span></span>
}
</div> <br>
} <a class="ha-reversefilter" asp-controller="Index" asp-action="Index">← Briefübersicht</a>
}
@if (Model.SearchType == SearchType.Register)
{
<span><span class="">Registereinträge</span>, die »@Model.ActiveSearch« enthalten.&emsp;</span>
<br>
<a class="ha-reversefilter" asp-controller="Register" asp-action="Allgemein">← Register</a>
<span></span>
}
@if (Model.SearchType == SearchType.Science)
{
<span><span class="">Bibliografische Einträge</span>, die »@Model.ActiveSearch«
enthalten.&emsp;</span>
<br>
<a class="ha-reversefilter" asp-controller="Register" asp-action="Forschung">←
Forschungsbibliographie</a>
<span></span>
}
<form id="ha-searchform" method="get">
<div class="ha-searchform">
<input id="ha-searchformtext" name="search" type="text" placeholder="Suchbegriff" value="@Model.ActiveSearch"/>
<button id="ha-searchformsubmit" type="submit">Suchen</button>
</div>
@if (Model.SearchType == SearchType.Letters) {
<div class="ha-includecomments">
<input type="checkbox" id="comments" name="comments" value="true" @(Model.IncludeComments == true ? "checked" : "")>
<label for="comments">Stellenkommentare einbeziehen</label>
</div> </div>
} }
</form>
<div class="ha-alternativesearches"> <form id="ha-searchform" method="get" hx-boost="false">
@if (Model.SearchType != SearchType.Letters) { <div class="ha-searchform">
<a asp-controller="Suche" asp-action="Briefe" asp-route-search="@Model.ActiveSearch" asp-route-comments="true" > <input id="ha-searchformtext" name="search" type="text" placeholder="Suchbegriff"
Briefe & Stellenkommentare nach »@Model.ActiveSearch« durchsuchen&nbsp;→ value="@Model.ActiveSearch" />
</a> <button id="ha-searchformsubmit" type="submit">Suchen</button>
} </div>
@if (Model.SearchType != SearchType.Register) { @if (Model.SearchType == SearchType.Letters)
<a asp-controller="Suche" asp-action="Register" asp-route-search="@Model.ActiveSearch" > {
Register nach »@Model.ActiveSearch« durchsuchen&nbsp;→ <div class="ha-includecomments">
</a> <input type="checkbox" id="comments" name="comments" value="true" @(Model.IncludeComments == true ?
} "checked" : "")>
@if (Model.SearchType != SearchType.Science) { <label for="comments">Stellenkommentare einbeziehen</label>
<a asp-controller="Suche" asp-action="Science" asp-route-search="@Model.ActiveSearch" > </div>
Forschungsbibliographie nach »@Model.ActiveSearch« durchsuchen&nbsp;→ }
</a> </form>
}
</div> <div class="ha-alternativesearches">
@if (Model.SearchType != SearchType.Letters)
{
<a asp-controller="Suche" asp-action="Briefe" asp-route-search="@Model.ActiveSearch"
asp-route-comments="true">
Briefe & Stellenkommentare nach »@Model.ActiveSearch« durchsuchen&nbsp;→
</a>
}
@if (Model.SearchType != SearchType.Register)
{
<a asp-controller="Suche" asp-action="Register" asp-route-search="@Model.ActiveSearch">
Register nach »@Model.ActiveSearch« durchsuchen&nbsp;→
</a>
}
@if (Model.SearchType != SearchType.Science)
{
<a asp-controller="Suche" asp-action="Science" asp-route-search="@Model.ActiveSearch">
Forschungsbibliographie nach »@Model.ActiveSearch« durchsuchen&nbsp;→
</a>
}
</div>
</div> </div>
<div class="ha-searchnav"> <div class="ha-searchnav">
@if (Model.AvailablePages != null && Model.AvailablePages.Any() && Model.AvailablePages.Count > 1) { @if (Model.AvailablePages != null && Model.AvailablePages.Any() && Model.AvailablePages.Count > 1)
@for(var i = 0; i < Model.AvailablePages.Count; i++) { {
<a class="@(Model.ActivePage == i ? "active" : "")" asp-route-search="@Model.ActiveSearch" asp-controller="Suche" asp-route-page="@i" asp-route-comments="@(Model.IncludeComments == true ? "true" : "")"> @for (var i = 0; i < Model.AvailablePages.Count; i++)
<span> {
@Model.AvailablePages[i] <a class="@(Model.ActivePage == i ? "active" : "")" asp-route-search="@Model.ActiveSearch"
</span> asp-controller="Suche" asp-route-page="@i"
</a> asp-route-comments="@(Model.IncludeComments == true ? "true" : "")">
<span>
@Model.AvailablePages[i]
</span>
</a>
}
} }
}
</div> </div>
</div> </div>
<div class="ha-searchbody"> <div class="ha-searchbody">
@* Letter & Marginal Search *@ @* Letter & Marginal Search *@
@if (Model.Letters != null) { @if (Model.Letters != null)
{
<div class="ha-letterlist"> <div class="ha-letterlist">
@foreach (var year in Model.Letters) { @foreach (var year in Model.Letters)
foreach (var letter in year.LetterList) { {
<div class="ha-letterlistentry"> foreach (var letter in year.LetterList)
<a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID"> {
@Html.Partial("/Views/Shared/_LetterHead.cshtml", (letter, true, false)) <div class="ha-letterlistentry">
</a> <a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID">
@Html.Partial("/Views/Shared/_LetterHead.cshtml", (letter, true, false))
</a>
@if (Model.SearchResults != null && Model.SearchResults.ContainsKey(letter.Meta.ID)) { @if (Model.SearchResults != null && Model.SearchResults.ContainsKey(letter.Meta.ID))
<div class="ha-letterlistsearchresults"> {
@foreach (var sr in Model.SearchResults[letter.Meta.ID]) <div class="ha-letterlistsearchresults">
{ @foreach (var sr in Model.SearchResults[letter.Meta.ID])
<div class="ha-letterlistsearchresult"> {
<div class="ha-searchresultlocation"> <div class="ha-letterlistsearchresult">
<a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID" asp-route-search="@Model.ActiveSearch" asp-fragment="@sr.Page-@sr.Line"> <div class="ha-searchresultlocation">
HKB @letter.Meta.ID @sr.Page/@sr.Line <a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID"
</a> asp-route-search="@Model.ActiveSearch" asp-fragment="@sr.Page-@sr.Line">
</div> HKB @letter.Meta.ID @sr.Page/@sr.Line
<div class="ha-searchresultpreview"> </a>
<a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID" asp-route-search="@Model.ActiveSearch" asp-fragment="@sr.Page-@sr.Line"> </div>
@sr.Preview <div class="ha-searchresultpreview">
</a> <a asp-controller="Briefe" asp-action="Index" asp-route-id="@letter.Meta.ID"
@if (Model.Marginals != null && Model.Marginals.Any()) { asp-route-search="@Model.ActiveSearch" asp-fragment="@sr.Page-@sr.Line">
@if (Model.Marginals.ContainsKey(letter.Meta.ID)) { @sr.Preview
@foreach (var c in Model.Marginals[letter.Meta.ID]) { </a>
@if (c.Item1.Page == sr.Page && c.Item1.Line == sr.Line) { @if (Model.Marginals != null && Model.Marginals.Any())
<div class="ha-seachresultmarginal"> {
<div class="ha-searchresultcommentpill">Kommentar</div> @if (Model.Marginals.ContainsKey(letter.Meta.ID))
@Html.Raw(c.Item2) {
</div> @foreach (var c in Model.Marginals[letter.Meta.ID])
} {
} @if (c.Item1.Page == sr.Page && c.Item1.Line == sr.Line)
} {
<div class="ha-seachresultmarginal">
<div class="ha-searchresultcommentpill">Kommentar</div>
@Html.Raw(c.Item2)
</div>
}
}
}
}
</div>
</div>
} }
</div> </div>
</div> }
}
</div> </div>
} }
</div>
} }
}
</div> </div>
} }
@* Register Search *@ @* Register Search *@
@if (Model.Comments != null && Model.Comments.Any()) { @if (Model.Comments != null && Model.Comments.Any())
{
<div class="ha-commentlist @(Model.SearchType == SearchType.Science ? "ha-forschung" : "")"> <div class="ha-commentlist @(Model.SearchType == SearchType.Science ? "ha-forschung" : "")">
@foreach (var k in Model.Comments) { @foreach (var k in Model.Comments)
<div class="ha-comment"> {
<div class="ha-headcomment">@Html.Raw(k.ParsedComment)</div> <div class="ha-comment">
@if (k.ParsedSubComments != null ) { <div class="ha-headcomment">@Html.Raw(k.ParsedComment)</div>
@foreach (var sk in k.ParsedSubComments) { @if (k.ParsedSubComments != null)
<div class="ha-subcomment">@Html.Raw(sk)</div> {
@foreach (var sk in k.ParsedSubComments)
{
<div class="ha-subcomment">@Html.Raw(sk)</div>
}
} }
} </div>
</div> }
}
</div> </div>
} }
@if (Model.SearchResultType == SearchResultType.NotFound) { @if (Model.SearchResultType == SearchResultType.NotFound)
<div class="ha-commentlist"> {
<div class="ha-commentlist">
Keine Treffer für »@Model.ActiveSearch«. Keine Treffer für »@Model.ActiveSearch«.
</div> </div>
} }
@if (Model.SearchResultType == SearchResultType.InvalidSearchTerm) { @if (Model.SearchResultType == SearchResultType.InvalidSearchTerm)
{
<div class="ha-commentlist"> <div class="ha-commentlist">
»@Model.ActiveSearch« ist ein ungültiger Suchbegriff. Die Suche darf nicht leer sein und nicht ausschließlich aus Spatien bestehen. »@Model.ActiveSearch« ist ein ungültiger Suchbegriff. Die Suche darf nicht leer sein und nicht
</div> ausschließlich aus Spatien bestehen.
} </div>
}
</div> </div>
</div> </div>

View File

@@ -13,11 +13,11 @@
}, },
"AllowedWebSocketConnections": "*", "AllowedWebSocketConnections": "*",
"AllowedHosts": "*", "AllowedHosts": "*",
"HamannFileStoreLinux": "/home/simon/test/", "HamannFileStoreLinux": "/Users/simon/test/",
"HamannFileStoreWindows": "C:/Users/simon/Downloads/test/", "HamannFileStoreWindows": "C:/Users/simon/Downloads/test/",
"BareRepositoryPathLinux": "/home/simon/source/hamann-xml/.git/", "BareRepositoryPathLinux": "/Users/simon/source/hamann-xml/.git/",
"BareRepositoryPathWindows": "D:/Simon/source/hamann-xml/.git/", "BareRepositoryPathWindows": "D:/Simon/source/hamann-xml/.git/",
"WorkingTreePathLinux": "/home/simon/source/hamann-xml/", "WorkingTreePathLinux": "/Users/simon/source/hamann-xml/",
"WorkingTreePathWindows": "D:/Simon/source/hamann-xml/", "WorkingTreePathWindows": "D:/Simon/source/hamann-xml/",
"RepositoryBranch": "Release", "RepositoryBranch": "Release",
"RepositoryURL": "https://github.com/Theodor-Springmann-Stiftung/hamann-xml", "RepositoryURL": "https://github.com/Theodor-Springmann-Stiftung/hamann-xml",

View File

@@ -4,7 +4,7 @@
"version": "0.0.0", "version": "0.0.0",
"type": "module", "type": "module",
"scripts": { "scripts": {
"dev": "vite", "dev": "vite build --watch",
"build": "vite build", "build": "vite build",
"preview": "vite preview" "preview": "vite preview"
}, },