Merge branch 'main' into reduce-bundle

This commit is contained in:
SleeplessOne1917 2023-06-23 03:31:29 +00:00 committed by GitHub
commit a2568a41f3
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
14 changed files with 165 additions and 140 deletions

2
.github/CODEOWNERS vendored
View file

@ -1 +1 @@
* @dessalines @SleeplessOne1917 @alectrocute * @dessalines @SleeplessOne1917 @alectrocute @jsit

View file

@ -1,32 +1,29 @@
name: "\U0001F41E Bug Report" name: "\U0001F41E Bug report"
description: Create a report to help us improve lemmy-ui description: Report a bug to help us improve Lemmy-UI.
title: "[Bug]: "
labels: ["bug", "triage"] labels: ["bug", "triage"]
body: body:
- type: markdown - type: markdown
attributes: attributes:
value: | value: |
Found a bug? Please fill out the sections below. 👍 Thanks for taking the time to help improve Lemmy-UI by reporting a bug!
Thanks for taking the time to fill out this bug report!
For backend issues, use [lemmy](https://github.com/LemmyNet/lemmy/issues/new/choose)
- type: checkboxes - type: checkboxes
attributes: attributes:
label: Requirements label: Requirements
description: Before you create a bug report please do the following. description: Before you create a bug report, please carefully check the following
options: options:
- label: Is this a bug report? For questions or discussions use https://lemmy.ml/c/lemmy_support - label: This is a bug report, and if not, please post to https://lemmy.ml/c/lemmy_support instead.
required: true required: true
- label: Did you check to see if this issue already exists? - label: Please [check](https://github.com/LemmyNet/lemmy-ui/issues) to see if this issue already exists.
required: true required: true
- label: Is this only a single bug? Do not put multiple bugs in one issue. - label: It's a single bug. Do not report multiple bugs in one issue.
required: true
- label: It's a frontend issue, not a backend issue; Otherwise please create an issue on the [backend repo](https://github.com/LemmyNet/lemmy) instead.
required: true required: true
- label: Is this a server side (not related to the UI) issue? Use the [Lemmy back end](https://github.com/LemmyNet/lemmy) repo.
required: false
- type: textarea - type: textarea
id: summary id: summary
attributes: attributes:
label: Summary label: Summary
description: A summary of the bug. description: Explain the bug and upload images, screenshots or videos if possible.
validations: validations:
required: true required: true
- type: textarea - type: textarea
@ -34,12 +31,13 @@ body:
attributes: attributes:
label: Steps to Reproduce label: Steps to Reproduce
description: | description: |
Describe the steps to reproduce the bug. In a numbered list, walk us through the steps needed to reproduce the bug.
The better your description is _(go 'here', click 'there'...)_ the fastest you'll get an _(accurate)_ resolution. The better your description is _(go 'here', click 'there'...)_, the quicker we can fix it.
value: | value: |
1. 1.
2. 2.
3. 3.
4.
validations: validations:
required: true required: true
- type: textarea - type: textarea
@ -47,20 +45,21 @@ body:
attributes: attributes:
label: Technical Details label: Technical Details
description: | description: |
- Any browser console errors? Describe your environment (OS, browser, model of smartphone, etc)
If relevant, also share any console errors and/or screenshots here.
validations: validations:
required: true required: true
- type: input - type: input
id: lemmy-ui-version id: lemmy-ui-version
attributes: attributes:
label: Version label: Lemmy Instance Version
description: Which Lemmy UI version do you use? Displayed in the footer. description: What's the version of the Lemmy instance where the bug can be reproduced?
placeholder: ex. 0.17.4-rc.4 placeholder: ex. 0.18-rc.6
validations: validations:
required: true required: true
- type: input - type: input
id: lemmy-instance id: lemmy-instance
attributes: attributes:
label: Lemmy Instance URL label: Lemmy Instance URL
description: Which Lemmy instance do you use? The address description: What's the URL of the Lemmy instance where the bug can be reproduced?
placeholder: lemmy.ml, lemmy.world, etc placeholder: https://lemmy.ml

View file

@ -1,54 +1,27 @@
name: "\U0001F680 Feature request" name: "\U0001F680 Feature request"
description: Suggest an idea for improving Lemmy's UI description: Suggest an idea for Lemmy-UI.
labels: ["enhancement"] labels: ["enhancement"]
body: body:
- type: markdown - type: markdown
attributes: attributes:
value: | value: |
Have a suggestion about Lemmy's UI? Thanks for taking the time to help improve Lemmy-UI by suggesting a feature!
For backend issues, use [lemmy](https://github.com/LemmyNet/lemmy/issues/new/choose)
- type: checkboxes - type: checkboxes
attributes: attributes:
label: Requirements label: Requirements
description: Before you create a feature request please do the following. description: Before you create a feature request, please carefully check the following
options: options:
- label: Is this a feature request? For questions or discussions use https://lemmy.ml/c/lemmy_support - label: This is a feature request and not a bug report. Otherwise, please create a new [bug report](https://github.com/LemmyNet/lemmy-ui/issues/new?assignees=&labels=bug%2Ctriage&projects=&template=BUG_REPORT.yml) instead.
required: true required: true
- label: Did you check to see if this issue already exists? - label: Please [check](https://github.com/LemmyNet/lemmy-ui/issues) to see if this request (or a similar one) already exists.
required: true required: true
- label: Is this only a feature request? Do not put multiple feature requests in one issue. - label: It's a single feature. Please don't request multiple features in one issue.
required: true required: true
- label: Is this a server side (not related to the UI) issue? Use the [Lemmy back end](https://github.com/LemmyNet/lemmy) repo.
required: false
- type: textarea
id: problem
attributes:
label: Is your proposal related to a problem?
description: |
Provide a clear and concise description of what the problem is.
For example, "I'm always frustrated when..."
validations:
required: true
- type: textarea - type: textarea
id: solution id: solution
attributes: attributes:
label: Describe the solution you'd like. label: Describe the feature you'd like
description: | description: |
Provide a clear and concise description of what you want to happen. Provide a clear and concise description of the feature. Explain why it's needed.
validations: validations:
required: true required: true
- type: textarea
id: alternatives
attributes:
label: Describe alternatives you've considered.
description: |
Let us know about other solutions you've tried or researched.
validations:
required: true
- type: textarea
id: context
attributes:
label: Additional context
description: |
Is there anything else you can add about the proposal?
You might want to link to related issues here, if you haven't already.

View file

@ -1,17 +0,0 @@
name: "? Question"
description: General questions about Lemmy
title: "Question: "
labels: ["question", "triage"]
body:
- type: markdown
attributes:
value: |
Have a question about Lemmy's UI?
Please check the docs first: https://join-lemmy.org/docs/en/index.html
- type: textarea
id: question
attributes:
label: Question
description: What's the question you have about Lemmy's UI?
validations:
required: true

8
.github/ISSUE_TEMPLATE/config.yml vendored Normal file
View file

@ -0,0 +1,8 @@
blank_issues_enabled: false
contact_links:
- name: Question
url: https://lemmy.ml/c/lemmy_support
about: Please ask and answer general questions here.
- name: Technical Discussion
url: https://github.com/LemmyNet/lemmy-ui/discussions
about: Please discuss technical topics with other contributors here.

View file

@ -1,11 +0,0 @@
name: "Hexbear"
description: For hexbear issues
labels: ["hexbear", "triage"]
body:
- type: textarea
id: question
attributes:
label: Question
description: What's the question you have about hexbear?
validations:
required: true

View file

@ -1,6 +1,6 @@
{ {
"name": "lemmy-ui", "name": "lemmy-ui",
"version": "0.18.0-rc.6", "version": "0.18.0-rc.7",
"description": "An isomorphic UI for lemmy", "description": "An isomorphic UI for lemmy",
"repository": "https://github.com/LemmyNet/lemmy-ui", "repository": "https://github.com/LemmyNet/lemmy-ui",
"license": "AGPL-3.0", "license": "AGPL-3.0",

View file

@ -642,7 +642,7 @@ export class Home extends Component<any, HomeState> {
const siteRes = this.state.siteRes; const siteRes = this.state.siteRes;
if (dataType === DataType.Post) { if (dataType === DataType.Post) {
switch (this.state.postsRes.state) { switch (this.state.postsRes?.state) {
case "loading": case "loading":
return ( return (
<h5> <h5>

View file

@ -691,6 +691,10 @@ export class Modlog extends Component<
} }
} }
async componentDidMount() {
await this.refetch();
}
get combined() { get combined() {
const res = this.state.res; const res = this.state.res;
const combined = res.state == "success" ? buildCombined(res.data) : []; const combined = res.state == "success" ? buildCombined(res.data) : [];

View file

@ -449,7 +449,6 @@ export class Inbox extends Component<any, InboxState> {
]} ]}
viewType={CommentViewType.Flat} viewType={CommentViewType.Flat}
finished={this.state.finished} finished={this.state.finished}
noIndent
markable markable
showCommunity showCommunity
showContext showContext
@ -489,7 +488,6 @@ export class Inbox extends Component<any, InboxState> {
]} ]}
finished={this.state.finished} finished={this.state.finished}
viewType={CommentViewType.Flat} viewType={CommentViewType.Flat}
noIndent
markable markable
showCommunity showCommunity
showContext showContext
@ -567,7 +565,6 @@ export class Inbox extends Component<any, InboxState> {
nodes={commentsToFlatNodes(replies)} nodes={commentsToFlatNodes(replies)}
viewType={CommentViewType.Flat} viewType={CommentViewType.Flat}
finished={this.state.finished} finished={this.state.finished}
noIndent
markable markable
showCommunity showCommunity
showContext showContext
@ -617,7 +614,6 @@ export class Inbox extends Component<any, InboxState> {
nodes={[{ comment_view: umv, children: [], depth: 0 }]} nodes={[{ comment_view: umv, children: [], depth: 0 }]}
viewType={CommentViewType.Flat} viewType={CommentViewType.Flat}
finished={this.state.finished} finished={this.state.finished}
noIndent
markable markable
showCommunity showCommunity
showContext showContext

View file

@ -145,7 +145,6 @@ export class PersonDetails extends Component<PersonDetailsProps, any> {
finished={this.props.finished} finished={this.props.finished}
admins={this.props.admins} admins={this.props.admins}
noBorder noBorder
noIndent
showCommunity showCommunity
showContext showContext
enableDownvotes={this.props.enableDownvotes} enableDownvotes={this.props.enableDownvotes}

View file

@ -381,33 +381,30 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
createdLine() { createdLine() {
const post_view = this.postView; const post_view = this.postView;
return ( return (
<ul className="list-inline mb-1 text-muted small mt-2"> <span className="small">
<li className="list-inline-item"> <PersonListing person={post_view.creator} />
<PersonListing person={post_view.creator} /> {this.creatorIsMod_ && (
<span className="mx-1 badge text-bg-light">
{this.creatorIsMod_ && ( {I18NextService.i18n.t("mod")}
<span className="mx-1 badge text-bg-light"> </span>
{I18NextService.i18n.t("mod")} )}
</span> {this.creatorIsAdmin_ && (
)} <span className="mx-1 badge text-bg-light">
{this.creatorIsAdmin_ && ( {I18NextService.i18n.t("admin")}
<span className="mx-1 badge text-bg-light"> </span>
{I18NextService.i18n.t("admin")} )}
</span> {post_view.creator.bot_account && (
)} <span className="mx-1 badge text-bg-light">
{post_view.creator.bot_account && ( {I18NextService.i18n.t("bot_account").toLowerCase()}
<span className="mx-1 badge text-bg-light"> </span>
{I18NextService.i18n.t("bot_account").toLowerCase()} )}
</span> {this.props.showCommunity && (
)} <>
{this.props.showCommunity && ( {" "}
<> {I18NextService.i18n.t("to")}{" "}
{" "} <CommunityLink community={post_view.community} />
{I18NextService.i18n.t("to")}{" "} </>
<CommunityLink community={post_view.community} /> )}
</>
)}
</li>
{post_view.post.language_id !== 0 && ( {post_view.post.language_id !== 0 && (
<span className="mx-1 badge text-bg-light"> <span className="mx-1 badge text-bg-light">
{ {
@ -416,17 +413,13 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
)?.name )?.name
} }
</span> </span>
)} )}{" "}
<li className="list-inline-item"></li> {" "}
<li className="list-inline-item"> <MomentTime
<span> published={post_view.post.published}
<MomentTime updated={post_view.post.updated}
published={post_view.post.published} />
updated={post_view.post.updated} </span>
/>
</span>
</li>
</ul>
); );
} }
@ -767,10 +760,8 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
to={`/post/${post_view.post.id}?scrollToComments=true`} to={`/post/${post_view.post.id}?scrollToComments=true`}
data-tippy-content={title} data-tippy-content={title}
> >
<span className="me-1"> <Icon icon="message-square" classes="me-1" inline />
<Icon icon="message-square" classes="me-1" inline /> {post_view.counts.comments}
{post_view.counts.comments}
</span>
{this.unreadCount && ( {this.unreadCount && (
<span className="text-muted fst-italic"> <span className="text-muted fst-italic">
({this.unreadCount} {I18NextService.i18n.t("new")}) ({this.unreadCount} {I18NextService.i18n.t("new")})
@ -1104,7 +1095,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
const post_view = this.postView; const post_view = this.postView;
return ( return (
this.state.showAdvanced && ( this.state.showAdvanced && (
<> <div className="mt-3">
{this.canMod_ && ( {this.canMod_ && (
<> <>
{!this.creatorIsMod_ && {!this.creatorIsMod_ &&
@ -1265,7 +1256,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
)} )}
</> </>
)} )}
</> </div>
) )
); );
} }
@ -1460,11 +1451,11 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
); );
} }
showMobilePreview() { showBodyPreview() {
const { body, id } = this.postView.post; const { body, id } = this.postView.post;
return !this.showBody && body ? ( return !this.showBody && body ? (
<Link className="text-body" to={`/post/${id}`}> <Link className="text-body mt-2 d-block" to={`/post/${id}`}>
<div className="md-div mb-1 preview-lines">{body}</div> <div className="md-div mb-1 preview-lines">{body}</div>
</Link> </Link>
) : ( ) : (
@ -1485,7 +1476,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
{this.mobileThumbnail()} {this.mobileThumbnail()}
{/* Show a preview of the post body */} {/* Show a preview of the post body */}
{this.showMobilePreview()} {this.showBodyPreview()}
{this.commentsLine(true)} {this.commentsLine(true)}
{this.userActionsLine()} {this.userActionsLine()}
@ -1507,6 +1498,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
<div className="col-12"> <div className="col-12">
{this.postTitleLine()} {this.postTitleLine()}
{this.createdLine()} {this.createdLine()}
{this.showBodyPreview()}
{this.commentsLine()} {this.commentsLine()}
{this.duplicatesLine()} {this.duplicatesLine()}
{this.userActionsLine()} {this.userActionsLine()}

View file

@ -25,4 +25,14 @@ export const fetchLimit = 40;
export const relTags = "noopener nofollow"; export const relTags = "noopener nofollow";
export const emDash = "\u2014"; export const emDash = "\u2014";
/**
* Accepted formats:
* !community@server.com
* /c/community@server.com
* /m/community@server.com
* /u/username@server.com
*/
export const instanceLinkRegex =
/(\/[cmu]\/|!)[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}/g;
export const testHost = "0.0.0.0:8536"; export const testHost = "0.0.0.0:8536";

View file

@ -14,6 +14,7 @@ import markdown_it_sub from "markdown-it-sub";
import markdown_it_sup from "markdown-it-sup"; import markdown_it_sup from "markdown-it-sup";
import Renderer from "markdown-it/lib/renderer"; import Renderer from "markdown-it/lib/renderer";
import Token from "markdown-it/lib/token"; import Token from "markdown-it/lib/token";
import { instanceLinkRegex } from "./config";
export let Tribute: any; export let Tribute: any;
@ -72,6 +73,75 @@ const html5EmbedConfig = {
}, },
}; };
function localInstanceLinkParser(md: MarkdownIt) {
md.core.ruler.push("replace-text", state => {
for (let i = 0; i < state.tokens.length; i++) {
if (state.tokens[i].type !== "inline") {
continue;
}
const inlineTokens: Token[] = state.tokens[i].children || [];
for (let j = inlineTokens.length - 1; j >= 0; j--) {
if (
inlineTokens[j].type === "text" &&
new RegExp(instanceLinkRegex).test(inlineTokens[j].content)
) {
const text = inlineTokens[j].content;
const matches = Array.from(text.matchAll(instanceLinkRegex));
let lastIndex = 0;
const newTokens: Token[] = [];
let linkClass = "community-link";
for (const match of matches) {
// If there is plain text before the match, add it as a separate token
if (match.index !== undefined && match.index > lastIndex) {
const textToken = new state.Token("text", "", 0);
textToken.content = text.slice(lastIndex, match.index);
newTokens.push(textToken);
}
let href;
if (match[0].startsWith("!")) {
href = "/c/" + match[0].substring(1);
} else if (match[0].startsWith("/m/")) {
href = "/c/" + match[0].substring(3);
} else {
href = match[0];
if (match[0].startsWith("/u/")) {
linkClass = "user-link";
}
}
const linkOpenToken = new state.Token("link_open", "a", 1);
linkOpenToken.attrs = [
["href", href],
["class", linkClass],
];
const textToken = new state.Token("text", "", 0);
textToken.content = match[0];
const linkCloseToken = new state.Token("link_close", "a", -1);
newTokens.push(linkOpenToken, textToken, linkCloseToken);
lastIndex =
(match.index !== undefined ? match.index : 0) + match[0].length;
}
// If there is plain text after the last match, add it as a separate token
if (lastIndex < text.length) {
const textToken = new state.Token("text", "", 0);
textToken.content = text.slice(lastIndex);
newTokens.push(textToken);
}
inlineTokens.splice(j, 1, ...newTokens);
}
}
}
});
}
export function setupMarkdown() { export function setupMarkdown() {
const markdownItConfig: MarkdownIt.Options = { const markdownItConfig: MarkdownIt.Options = {
html: false, html: false,
@ -88,7 +158,8 @@ export function setupMarkdown() {
.use(markdown_it_sup) .use(markdown_it_sup)
.use(markdown_it_footnote) .use(markdown_it_footnote)
.use(markdown_it_html5_embed, html5EmbedConfig) .use(markdown_it_html5_embed, html5EmbedConfig)
.use(markdown_it_container, "spoiler", spoilerConfig); .use(markdown_it_container, "spoiler", spoilerConfig)
.use(localInstanceLinkParser);
// .use(markdown_it_emoji, { // .use(markdown_it_emoji, {
// defs: emojiDefs, // defs: emojiDefs,
// }); // });
@ -99,6 +170,7 @@ export function setupMarkdown() {
.use(markdown_it_footnote) .use(markdown_it_footnote)
.use(markdown_it_html5_embed, html5EmbedConfig) .use(markdown_it_html5_embed, html5EmbedConfig)
.use(markdown_it_container, "spoiler", spoilerConfig) .use(markdown_it_container, "spoiler", spoilerConfig)
.use(localInstanceLinkParser)
// .use(markdown_it_emoji, { // .use(markdown_it_emoji, {
// defs: emojiDefs, // defs: emojiDefs,
// }) // })