mirror of
				https://github.com/superseriousbusiness/gotosocial.git
				synced 2025-10-30 23:02:25 -05:00 
			
		
		
		
	[feature] Add system message wrappers for pending replies and placeholder attachments (#3713)
Fixes #3712
This commit is contained in:
		
					parent
					
						
							
								493de5c005
							
						
					
				
			
			
				commit
				
					
						ab758cc233
					
				
			
		
					 2 changed files with 32 additions and 10 deletions
				
			
		|  | @ -1278,7 +1278,7 @@ func (suite *InternalToFrontendTestSuite) TestStatusToFrontendUnknownAttachments | ||||||
|   "muted": false, |   "muted": false, | ||||||
|   "bookmarked": false, |   "bookmarked": false, | ||||||
|   "pinned": false, |   "pinned": false, | ||||||
|   "content": "\u003cp\u003ehi \u003cspan class=\"h-card\"\u003e\u003ca href=\"http://localhost:8080/@admin\" class=\"u-url mention\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e@\u003cspan\u003eadmin\u003c/span\u003e\u003c/a\u003e\u003c/span\u003e here's some media for ya\u003c/p\u003e\u003chr\u003e\u003cp\u003e\u003ci lang=\"en\"\u003eℹ️ Note from localhost:8080: 2 attachments in this status were not downloaded. Treat the following external links with care:\u003c/i\u003e\u003c/p\u003e\u003cul\u003e\u003cli\u003e\u003ca href=\"http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE7ZGJYTSYMXF927GF9353KR.svg\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e01HE7ZGJYTSYMXF927GF9353KR.svg\u003c/a\u003e [SVG line art of a sloth, public domain]\u003c/li\u003e\u003cli\u003e\u003ca href=\"http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE892Y8ZS68TQCNPX7J888P3.mp3\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e01HE892Y8ZS68TQCNPX7J888P3.mp3\u003c/a\u003e [Jolly salsa song, public domain.]\u003c/li\u003e\u003c/ul\u003e", |   "content": "\u003cp\u003ehi \u003cspan class=\"h-card\"\u003e\u003ca href=\"http://localhost:8080/@admin\" class=\"u-url mention\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e@\u003cspan\u003eadmin\u003c/span\u003e\u003c/a\u003e\u003c/span\u003e here's some media for ya\u003c/p\u003e\u003cdiv class=\"gts-system-message gts-placeholder-attachments\"\u003e\u003chr\u003e\u003cp\u003e\u003ci lang=\"en\"\u003eℹ️ Note from localhost:8080: 2 attachments in this status were not downloaded. Treat the following external links with care:\u003c/i\u003e\u003c/p\u003e\u003cul\u003e\u003cli\u003e\u003ca href=\"http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE7ZGJYTSYMXF927GF9353KR.svg\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e01HE7ZGJYTSYMXF927GF9353KR.svg\u003c/a\u003e [SVG line art of a sloth, public domain]\u003c/li\u003e\u003cli\u003e\u003ca href=\"http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE892Y8ZS68TQCNPX7J888P3.mp3\" rel=\"nofollow noreferrer noopener\" target=\"_blank\"\u003e01HE892Y8ZS68TQCNPX7J888P3.mp3\u003c/a\u003e [Jolly salsa song, public domain.]\u003c/li\u003e\u003c/ul\u003e\u003c/div\u003e", | ||||||
|   "reblog": null, |   "reblog": null, | ||||||
|   "account": { |   "account": { | ||||||
|     "id": "01FHMQX3GAABWSM0S2VZEC2SWC", |     "id": "01FHMQX3GAABWSM0S2VZEC2SWC", | ||||||
|  | @ -1828,7 +1828,7 @@ func (suite *InternalToFrontendTestSuite) TestStatusToAPIStatusPendingApproval() | ||||||
|   "muted": false, |   "muted": false, | ||||||
|   "bookmarked": false, |   "bookmarked": false, | ||||||
|   "pinned": false, |   "pinned": false, | ||||||
|   "content": "<p>Hi <span class=\"h-card\"><a href=\"http://localhost:8080/@1happyturtle\" class=\"u-url mention\" rel=\"nofollow noreferrer noopener\" target=\"_blank\">@<span>1happyturtle</span></a></span>, can I reply?</p><hr><p><i lang=\"en\">ℹ️ Note from localhost:8080: This reply is pending your approval. You can quickly accept it by liking, boosting or replying to it. You can also accept or reject it at the following link: <a href=\"http://localhost:8080/settings/user/interaction_requests/01J5QVXCCEATJYSXM9H6MZT4JR\" rel=\"noreferrer noopener nofollow\" target=\"_blank\">http://localhost:8080/settings/user/interaction_requests/01J5QVXCCEATJYSXM9H6MZT4JR</a>.</i></p>", |   "content": "<p>Hi <span class=\"h-card\"><a href=\"http://localhost:8080/@1happyturtle\" class=\"u-url mention\" rel=\"nofollow noreferrer noopener\" target=\"_blank\">@<span>1happyturtle</span></a></span>, can I reply?</p><div class=\"gts-system-message gts-pending-reply\"><hr><p><i lang=\"en\">ℹ️ Note from localhost:8080: This reply is pending your approval. You can quickly accept it by liking, boosting or replying to it. You can also accept or reject it at the following link: <a href=\"http://localhost:8080/settings/user/interaction_requests/01J5QVXCCEATJYSXM9H6MZT4JR\" rel=\"noreferrer noopener nofollow\" target=\"_blank\">http://localhost:8080/settings/user/interaction_requests/01J5QVXCCEATJYSXM9H6MZT4JR</a>.</i></p></div>", | ||||||
|   "reblog": null, |   "reblog": null, | ||||||
|   "application": { |   "application": { | ||||||
|     "name": "superseriousbusiness", |     "name": "superseriousbusiness", | ||||||
|  |  | ||||||
|  | @ -128,12 +128,14 @@ func misskeyReportInlineURLs(content string) []*url.URL { | ||||||
| // | // | ||||||
| // Example: | // Example: | ||||||
| // | // | ||||||
|  | //	<div class="gts-system-message gts-placeholder-attachments"> | ||||||
| //		<hr> | //		<hr> | ||||||
| //		<p><i lang="en">ℹ️ Note from your.instance.com: 2 attachment(s) in this status were not downloaded. Treat the following external link(s) with care:</i></p> | //		<p><i lang="en">ℹ️ Note from your.instance.com: 2 attachment(s) in this status were not downloaded. Treat the following external link(s) with care:</i></p> | ||||||
| //		<ul> | //		<ul> | ||||||
| //			<li><a href="http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE7ZGJYTSYMXF927GF9353KR.svg" rel="nofollow noreferrer noopener" target="_blank">01HE7ZGJYTSYMXF927GF9353KR.svg</a> [SVG line art of a sloth, public domain]</li> | //			<li><a href="http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE7ZGJYTSYMXF927GF9353KR.svg" rel="nofollow noreferrer noopener" target="_blank">01HE7ZGJYTSYMXF927GF9353KR.svg</a> [SVG line art of a sloth, public domain]</li> | ||||||
| //			<li><a href="http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE892Y8ZS68TQCNPX7J888P3.mp3" rel="nofollow noreferrer noopener" target="_blank">01HE892Y8ZS68TQCNPX7J888P3.mp3</a> [Jolly salsa song, public domain.]</li> | //			<li><a href="http://example.org/fileserver/01HE7Y659ZWZ02JM4AWYJZ176Q/attachment/original/01HE892Y8ZS68TQCNPX7J888P3.mp3" rel="nofollow noreferrer noopener" target="_blank">01HE892Y8ZS68TQCNPX7J888P3.mp3</a> [Jolly salsa song, public domain.]</li> | ||||||
| //		</ul> | //		</ul> | ||||||
|  | //	</div> | ||||||
| func placeholderAttachments(arr []*apimodel.Attachment) (string, []*apimodel.Attachment) { | func placeholderAttachments(arr []*apimodel.Attachment) (string, []*apimodel.Attachment) { | ||||||
| 
 | 
 | ||||||
| 	// Extract non-locally stored attachments into a | 	// Extract non-locally stored attachments into a | ||||||
|  | @ -187,7 +189,7 @@ func placeholderAttachments(arr []*apimodel.Attachment) (string, []*apimodel.Att | ||||||
| 	} | 	} | ||||||
| 	note.WriteString(`</ul>`) | 	note.WriteString(`</ul>`) | ||||||
| 
 | 
 | ||||||
| 	return text.SanitizeToHTML(note.String()), arr | 	return systemMessage("gts-placeholder-attachments", note.String()), arr | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func (c *Converter) pendingReplyNote( | func (c *Converter) pendingReplyNote( | ||||||
|  | @ -228,7 +230,27 @@ func (c *Converter) pendingReplyNote( | ||||||
| 	note.WriteString(`</a>.`) | 	note.WriteString(`</a>.`) | ||||||
| 	note.WriteString(`</i></p>`) | 	note.WriteString(`</i></p>`) | ||||||
| 
 | 
 | ||||||
| 	return text.SanitizeToHTML(note.String()), nil | 	return systemMessage("gts-pending-reply", note.String()), nil | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | // systemMessage wraps a note with a div with semantic classes that aren't allowed through the sanitizer, | ||||||
|  | // but may be emitted to the client as an addition to the status's actual content. | ||||||
|  | // Clients may want to display these specially or suppress them in favor of their own UI. | ||||||
|  | // | ||||||
|  | // messageClass must be valid inside an HTML attribute and should be one or more classes starting with `gts-`. | ||||||
|  | func systemMessage( | ||||||
|  | 	messageClass string, | ||||||
|  | 	unsanitizedNoteHTML string, | ||||||
|  | ) string { | ||||||
|  | 	var wrappedNote strings.Builder | ||||||
|  | 
 | ||||||
|  | 	wrappedNote.WriteString(`<div class="gts-system-message `) | ||||||
|  | 	wrappedNote.WriteString(messageClass) | ||||||
|  | 	wrappedNote.WriteString(`">`) | ||||||
|  | 	wrappedNote.WriteString(text.SanitizeToHTML(unsanitizedNoteHTML)) | ||||||
|  | 	wrappedNote.WriteString(`</div>`) | ||||||
|  | 
 | ||||||
|  | 	return wrappedNote.String() | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| // ContentToContentLanguage tries to | // ContentToContentLanguage tries to | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue