mirror of
https://seed.radicle.dev/rad:z4V1sjrXqjvFdnCUbxPFqd5p4DtH5.git
synced 2026-11-16 03:40:37 +08:00
Adding embed editing in issues and patches
This commit is contained in:
@@ -6,7 +6,7 @@ import type {
|
||||
Tree,
|
||||
DiffResponse,
|
||||
} from "./lib/project.js";
|
||||
import type { Comment } from "./lib/project/comment.js";
|
||||
import type { Comment, Embed } from "./lib/project/comment.js";
|
||||
import type {
|
||||
Commit,
|
||||
CommitBlob,
|
||||
@@ -52,6 +52,7 @@ export type {
|
||||
DiffContent,
|
||||
DiffFile,
|
||||
DiffResponse,
|
||||
Embed,
|
||||
HunkLine,
|
||||
Issue,
|
||||
IssueState,
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import type { Embed } from "@app/lib/file.js";
|
||||
import type { Commit, Commits } from "./project/commit.js";
|
||||
import type { Embed } from "./project/comment.js";
|
||||
import type { Fetcher, RequestOptions } from "./fetcher.js";
|
||||
import type {
|
||||
Issue,
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import type { Embed } from "@app/lib/file.js";
|
||||
import type { Comment } from "./comment.js";
|
||||
import type { Comment, Embed } from "./comment.js";
|
||||
import type { ZodSchema } from "zod";
|
||||
import { array, boolean, literal, object, string, union } from "zod";
|
||||
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import type { Embed } from "@app/lib/file.js";
|
||||
import type { Comment } from "./comment.js";
|
||||
import type { Comment, Embed } from "./comment.js";
|
||||
import type { ZodSchema, z } from "zod";
|
||||
|
||||
import { commentSchema } from "./comment.js";
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<script lang="ts" strictEvents>
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
import type { GroupedReactions } from "@app/lib/reactions";
|
||||
|
||||
import { tick } from "svelte";
|
||||
@@ -21,6 +21,7 @@
|
||||
export let body: string;
|
||||
export let enableAttachments: boolean = false;
|
||||
export let reactions: GroupedReactions | undefined = undefined;
|
||||
export let embeds: Map<string, Embed> | undefined = undefined;
|
||||
export let caption = "commented";
|
||||
export let rawPath: string;
|
||||
export let timestamp: number;
|
||||
@@ -145,6 +146,7 @@
|
||||
<ExtendedTextarea
|
||||
{rawPath}
|
||||
{body}
|
||||
{embeds}
|
||||
{enableAttachments}
|
||||
submitInProgress={state === "submit"}
|
||||
submitCaption="Save"
|
||||
@@ -152,7 +154,7 @@
|
||||
on:submit={async ({ detail: { comment, embeds } }) => {
|
||||
state = "submit";
|
||||
try {
|
||||
await editComment_(comment, embeds);
|
||||
await editComment_(comment, Array.from(embeds.values()));
|
||||
} finally {
|
||||
state = "read";
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<script lang="ts">
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
import ExtendedTextarea from "@app/components/ExtendedTextarea.svelte";
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
on:submit={async ({ detail: { comment, embeds } }) => {
|
||||
try {
|
||||
state = "submit";
|
||||
await submit(comment, embeds);
|
||||
await submit(comment, Array.from(embeds.values()));
|
||||
} finally {
|
||||
state = "collapsed";
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<script lang="ts" strictEvents>
|
||||
import type { Embed, EmbedWithOid } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
import { createEventDispatcher } from "svelte";
|
||||
|
||||
@@ -23,10 +23,10 @@
|
||||
export let inline: boolean = false;
|
||||
export let rawPath: string;
|
||||
export let body: string = "";
|
||||
export let embeds: Map<string, Embed> = new Map();
|
||||
export let submitInProgress: boolean = false;
|
||||
|
||||
let preview: boolean = false;
|
||||
let newEmbeds: EmbedWithOid[] = [];
|
||||
let selectionStart = 0;
|
||||
let selectionEnd = 0;
|
||||
let inputFiles: FileList | undefined = undefined;
|
||||
@@ -34,15 +34,14 @@
|
||||
const inputId = `input-label-${crypto.randomUUID()}`;
|
||||
|
||||
const dispatch = createEventDispatcher<{
|
||||
submit: { comment: string; embeds: Embed[] };
|
||||
submit: { comment: string; embeds: Map<string, Embed> };
|
||||
close: null;
|
||||
click: null;
|
||||
}>();
|
||||
|
||||
function submit() {
|
||||
dispatch("submit", { comment: body, embeds: newEmbeds });
|
||||
dispatch("submit", { comment: body, embeds });
|
||||
preview = false;
|
||||
newEmbeds = [];
|
||||
}
|
||||
|
||||
const MAX_BLOB_SIZE = 4_194_304;
|
||||
@@ -86,10 +85,10 @@
|
||||
}
|
||||
|
||||
function attachEmbeds(files: FileList) {
|
||||
const embeds = Array.from(files).map(embed);
|
||||
void Promise.all(embeds).then(embeds =>
|
||||
embeds.forEach(embed => {
|
||||
if (embed.content.length > MAX_BLOB_SIZE) {
|
||||
const embedPromise = Array.from(files).map(embed);
|
||||
void Promise.all(embedPromise).then(newEmbeds =>
|
||||
newEmbeds.forEach(({ oid, name, content }) => {
|
||||
if (content.length > MAX_BLOB_SIZE) {
|
||||
modal.show({
|
||||
component: ErrorModal,
|
||||
props: {
|
||||
@@ -103,15 +102,8 @@
|
||||
});
|
||||
return;
|
||||
}
|
||||
newEmbeds = [
|
||||
...newEmbeds,
|
||||
{
|
||||
oid: embed.oid,
|
||||
name: embed.name,
|
||||
content: embed.content,
|
||||
},
|
||||
];
|
||||
const embedText = `\n`;
|
||||
embeds.set(oid, { name, content });
|
||||
const embedText = `\n`;
|
||||
body = body
|
||||
.slice(0, selectionStart)
|
||||
.concat(embedText, body.slice(selectionEnd));
|
||||
@@ -196,7 +188,7 @@
|
||||
</Radio>
|
||||
{#if preview}
|
||||
<div class="preview">
|
||||
<Markdown {rawPath} content={body} embeds={newEmbeds} />
|
||||
<Markdown {rawPath} content={body} {embeds} />
|
||||
</div>
|
||||
{:else}
|
||||
<input
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<script lang="ts">
|
||||
import type { EmbedWithOid } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
import dompurify from "dompurify";
|
||||
import matter from "@radicle/gray-matter";
|
||||
@@ -28,7 +28,7 @@
|
||||
export let rawPath: string;
|
||||
// If present, means we are in a preview context,
|
||||
// use this for image previews instead of /raw URLs.
|
||||
export let embeds: EmbedWithOid[] | undefined = undefined;
|
||||
export let embeds: Map<string, Embed> | undefined = undefined;
|
||||
|
||||
let container: HTMLElement;
|
||||
let frontMatter: [string, any][] | undefined = undefined;
|
||||
@@ -112,10 +112,9 @@
|
||||
|
||||
// If the image is an oid embed
|
||||
if (imagePath && isCommit(imagePath)) {
|
||||
const embed = embeds?.find(e => {
|
||||
return e.oid === imagePath;
|
||||
});
|
||||
if (embed) {
|
||||
const embed = embeds?.get(imagePath);
|
||||
// If the embed content is the base64 encoded image, use it directly.
|
||||
if (embed && embed.content.startsWith("data:")) {
|
||||
i.setAttribute("src", embed.content);
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -20,10 +20,11 @@
|
||||
</script>
|
||||
|
||||
<script lang="ts" strictEvents>
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
import * as utils from "@app/lib/utils";
|
||||
import partial from "lodash/partial";
|
||||
import { parseEmbedIntoMap } from "@app/lib/file";
|
||||
import { tick } from "svelte";
|
||||
|
||||
import CommentComponent from "@app/components/Comment.svelte";
|
||||
@@ -88,13 +89,14 @@
|
||||
<div class="comments">
|
||||
<div class="top-level-comment" class:has-replies={replies.length > 0}>
|
||||
<CommentComponent
|
||||
{enableAttachments}
|
||||
{rawPath}
|
||||
id={root.id}
|
||||
authorId={root.author.id}
|
||||
authorAlias={root.author.alias}
|
||||
reactions={root.reactions}
|
||||
embeds={parseEmbedIntoMap(root.embeds)}
|
||||
timestamp={root.timestamp}
|
||||
disableEdit={root.embeds.length > 0}
|
||||
body={root.body}
|
||||
editComment={editComment &&
|
||||
canEditComment(root.author.id) &&
|
||||
@@ -107,6 +109,7 @@
|
||||
<div class="replies">
|
||||
{#each replies as reply}
|
||||
<CommentComponent
|
||||
{enableAttachments}
|
||||
{rawPath}
|
||||
id={reply.id}
|
||||
authorId={reply.author.id}
|
||||
@@ -115,8 +118,8 @@
|
||||
isReply
|
||||
isLastReply={replies[replies.length - 1] === reply}
|
||||
reactions={reply.reactions}
|
||||
embeds={parseEmbedIntoMap(reply.embeds)}
|
||||
timestamp={reply.timestamp}
|
||||
disableEdit={reply.embeds.length > 0}
|
||||
body={reply.body}
|
||||
editComment={editComment &&
|
||||
canEditComment(reply.author.id) &&
|
||||
|
||||
+9
-8
@@ -1,10 +1,4 @@
|
||||
export interface Embed {
|
||||
name: string;
|
||||
content: string;
|
||||
}
|
||||
export interface EmbedWithOid extends Embed {
|
||||
oid: string;
|
||||
}
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
async function parseGitOid(bytes: Uint8Array): Promise<string> {
|
||||
// Create the header
|
||||
@@ -38,6 +32,13 @@ function base64String(file: File): Promise<string> {
|
||||
});
|
||||
}
|
||||
|
||||
export function parseEmbedIntoMap(embeds: Embed[]) {
|
||||
return embeds.reduce((acc, embed) => {
|
||||
acc.set(embed.content.substring(4), embed);
|
||||
return acc;
|
||||
}, new Map());
|
||||
}
|
||||
|
||||
const mimes: Record<string, string> = {
|
||||
"3gp": "video/3gpp",
|
||||
"7z": "application/x-7z-compressed",
|
||||
@@ -101,7 +102,7 @@ const mimes: Record<string, string> = {
|
||||
zip: "application/zip",
|
||||
};
|
||||
|
||||
async function embed(file: File): Promise<EmbedWithOid> {
|
||||
async function embed(file: File) {
|
||||
const bytes = new Uint8Array(await file.arrayBuffer());
|
||||
const oid = await parseGitOid(bytes);
|
||||
const content = await base64String(file);
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<script lang="ts" strictEvents>
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type { Embed } from "@httpd-client";
|
||||
|
||||
import Badge from "@app/components/Badge.svelte";
|
||||
import Clipboard from "@app/components/Clipboard.svelte";
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
<script lang="ts">
|
||||
import type { Embed } from "@httpd-client/lib/project/comment";
|
||||
import type {
|
||||
BaseUrl,
|
||||
DiffResponse,
|
||||
Embed,
|
||||
PatchState,
|
||||
Verdict,
|
||||
} from "@httpd-client";
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
<script lang="ts">
|
||||
import type { BaseUrl, Issue, IssueState, Project } from "@httpd-client";
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type {
|
||||
BaseUrl,
|
||||
Issue,
|
||||
IssueState,
|
||||
Embed,
|
||||
Project,
|
||||
} from "@httpd-client";
|
||||
import type { Session } from "@app/lib/httpd";
|
||||
|
||||
import isEqual from "lodash/isEqual";
|
||||
@@ -15,6 +20,7 @@
|
||||
import { closeFocused } from "@app/components/Popover.svelte";
|
||||
import { groupReactions } from "@app/lib/reactions";
|
||||
import { httpdStore } from "@app/lib/httpd";
|
||||
import { parseEmbedIntoMap } from "@app/lib/file";
|
||||
|
||||
import AssigneeInput from "@app/views/projects/Cob/AssigneeInput.svelte";
|
||||
import Badge from "@app/components/Badge.svelte";
|
||||
@@ -358,14 +364,10 @@
|
||||
}
|
||||
}
|
||||
|
||||
$: embeds = issue.discussion.reduce(
|
||||
(acc, comment) => {
|
||||
acc[comment.id] = comment.embeds;
|
||||
return acc;
|
||||
},
|
||||
{} as Record<string, Embed[]>,
|
||||
$: uniqueEmbeds = uniqBy(
|
||||
issue.discussion.flatMap(comment => comment.embeds),
|
||||
"content",
|
||||
);
|
||||
$: uniqueEmbeds = uniqBy(Object.values(embeds).flat(), "content");
|
||||
$: selectedItem = issue.state.status === "closed" ? items[0] : items[1];
|
||||
$: threads = issue.discussion
|
||||
.filter(
|
||||
@@ -518,6 +520,7 @@
|
||||
<ExtendedTextarea
|
||||
rawPath={rawPath(project.head)}
|
||||
enableAttachments
|
||||
embeds={parseEmbedIntoMap(issue.discussion[0].embeds)}
|
||||
body={issue.discussion[0].body}
|
||||
submitCaption="Save"
|
||||
submitInProgress={issueState === "submit"}
|
||||
@@ -535,7 +538,7 @@
|
||||
issue.title,
|
||||
issue.id,
|
||||
comment,
|
||||
embeds,
|
||||
Array.from(embeds.values()),
|
||||
);
|
||||
} finally {
|
||||
issueState = "read";
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
<script lang="ts">
|
||||
import type { BaseUrl, Project } from "@httpd-client";
|
||||
import type { EmbedWithOid } from "@app/lib/file";
|
||||
import type { BaseUrl, Embed, Project } from "@httpd-client";
|
||||
|
||||
import * as modal from "@app/lib/modal";
|
||||
import * as router from "@app/lib/router";
|
||||
@@ -28,7 +27,6 @@
|
||||
export let rawPath: (commit?: string) => string;
|
||||
export let tracking: boolean;
|
||||
|
||||
let newEmbeds: EmbedWithOid[] = [];
|
||||
let preview: boolean = false;
|
||||
let selectionStart = 0;
|
||||
let selectionEnd = 0;
|
||||
@@ -41,6 +39,7 @@
|
||||
let creatingIssue: boolean = false;
|
||||
|
||||
const api = new HttpdClient(baseUrl);
|
||||
const newEmbeds = new Map<string, Embed>();
|
||||
|
||||
function handleFileDrop(event: { detail: DragEvent }) {
|
||||
event.detail.preventDefault();
|
||||
@@ -48,10 +47,7 @@
|
||||
const embeds = Array.from(event.detail.dataTransfer.files).map(embed);
|
||||
void Promise.all(embeds).then(embeds =>
|
||||
embeds.forEach(({ oid, name, content }) => {
|
||||
newEmbeds = [
|
||||
...newEmbeds,
|
||||
{ oid: oid, name: name, content: content },
|
||||
];
|
||||
newEmbeds.set(oid, { name, content });
|
||||
const embedText = `\n`;
|
||||
issueText = issueText
|
||||
.slice(0, selectionStart)
|
||||
|
||||
@@ -35,8 +35,7 @@
|
||||
</script>
|
||||
|
||||
<script lang="ts">
|
||||
import type { BaseUrl, Patch } from "@httpd-client";
|
||||
import type { Embed } from "@app/lib/file";
|
||||
import type { BaseUrl, Embed, Patch } from "@httpd-client";
|
||||
import type { PatchView } from "./router";
|
||||
import type { Route } from "@app/lib/router";
|
||||
import type { ComponentProps } from "svelte";
|
||||
@@ -45,10 +44,11 @@
|
||||
import * as role from "@app/lib/roles";
|
||||
import * as router from "@app/lib/router";
|
||||
import * as utils from "@app/lib/utils";
|
||||
import { HttpdClient } from "@httpd-client";
|
||||
import capitalize from "lodash/capitalize";
|
||||
import isEqual from "lodash/isEqual";
|
||||
import partial from "lodash/partial";
|
||||
import uniqBy from "lodash/uniqBy";
|
||||
import { HttpdClient } from "@httpd-client";
|
||||
import { httpdStore, type Session } from "@app/lib/httpd";
|
||||
|
||||
import Badge from "@app/components/Badge.svelte";
|
||||
@@ -60,6 +60,7 @@
|
||||
import CommitTeaser from "@app/views/projects/Commit/CommitTeaser.svelte";
|
||||
import DropdownList from "@app/components/DropdownList.svelte";
|
||||
import DropdownListItem from "@app/components/DropdownList/DropdownListItem.svelte";
|
||||
import Embeds from "@app/views/projects/Cob/Embeds.svelte";
|
||||
import ErrorModal from "@app/modals/ErrorModal.svelte";
|
||||
import ExtendedTextarea from "@app/components/ExtendedTextarea.svelte";
|
||||
import Icon from "@app/components/Icon.svelte";
|
||||
@@ -468,6 +469,12 @@
|
||||
revisionId = view.revision;
|
||||
}
|
||||
|
||||
$: uniqueEmbeds = uniqBy(
|
||||
patch.revisions.flatMap(({ discussions }) =>
|
||||
discussions.flatMap(comment => comment.embeds),
|
||||
),
|
||||
"content",
|
||||
);
|
||||
$: description = patch.revisions[0].description;
|
||||
$: newDescription = description;
|
||||
$: patchReviews = computeReviews(patch);
|
||||
@@ -961,6 +968,7 @@
|
||||
}
|
||||
}
|
||||
}} />
|
||||
<Embeds embeds={uniqueEmbeds} />
|
||||
</div>
|
||||
</div>
|
||||
</Layout>
|
||||
|
||||
@@ -1,5 +1,9 @@
|
||||
import { test, cobUrl, expect } from "@tests/support/fixtures.js";
|
||||
import { createProject, expectReactionsToWork } from "@tests/support/project";
|
||||
import {
|
||||
addEmbed,
|
||||
createProject,
|
||||
expectReactionsToWork,
|
||||
} from "@tests/support/project";
|
||||
|
||||
test("navigate single issue", async ({ page }) => {
|
||||
await page.goto(`${cobUrl}/issues`);
|
||||
@@ -127,3 +131,78 @@ test("add and remove reactions", async ({ page, authenticatedPeer }) => {
|
||||
.click();
|
||||
await expectReactionsToWork(page);
|
||||
});
|
||||
|
||||
test("handling embeds", async ({ page, authenticatedPeer }) => {
|
||||
const { rid } = await createProject(authenticatedPeer, "embeds");
|
||||
await page.goto(
|
||||
`/nodes/${authenticatedPeer.httpdBaseUrl.hostname}:${authenticatedPeer.httpdBaseUrl.port}/${rid}/issues/new`,
|
||||
);
|
||||
await page.getByPlaceholder("Title").fill("This is a title");
|
||||
await page
|
||||
.getByPlaceholder("Write a description")
|
||||
.fill("Here is some text\n\n");
|
||||
await addEmbed(
|
||||
page,
|
||||
"./public/images/radicle-228x228.png",
|
||||
"radicle-228x228.png",
|
||||
"image/png",
|
||||
);
|
||||
await expect(page.getByPlaceholder("Write a description")).toHaveValue(
|
||||
"Here is some text\n\n\n",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Preview" }).click();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
"data:image/png;base64,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",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Submit" }).click();
|
||||
await expect(page.getByRole("button", { name: "Submit" })).toBeHidden();
|
||||
await expect(page.getByText("This is a title")).toBeVisible();
|
||||
await expect(page.getByText("Here is some text")).toBeVisible();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
const { scheme, hostname, port } = authenticatedPeer.httpdBaseUrl;
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
`${scheme}://${hostname}:${port}/raw/rad:z2J7s48EbCBckcEmj2dm5eaFVoBsy/blobs/bae036309c2182c7304c97956969369823b5c6ad?mime=image/png`,
|
||||
);
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
|
||||
await page.getByRole("button", { name: "edit issue" }).click();
|
||||
await page
|
||||
.getByPlaceholder("Leave a description")
|
||||
.fill(
|
||||
"Here is some text\n\n\n\n",
|
||||
);
|
||||
await addEmbed(
|
||||
page,
|
||||
"./public/images/apple-touch-icon.png",
|
||||
"apple-touch-icon.png",
|
||||
"image/png",
|
||||
);
|
||||
await expect(page.getByPlaceholder("Leave a description")).toHaveValue(
|
||||
"Here is some text\n\n\n\n\n",
|
||||
);
|
||||
await page.getByRole("button", { name: "Save" }).click();
|
||||
await expect(page.getByRole("button", { name: "Submit" })).toBeHidden();
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "apple-touch-icon.png" }),
|
||||
).toBeVisible();
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
});
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { test, cobUrl, expect } from "@tests/support/fixtures.js";
|
||||
import { addEmbed, createProject } from "@tests/support/project";
|
||||
import { createProject } from "@tests/support/project";
|
||||
|
||||
test("navigate issue listing", async ({ page }) => {
|
||||
await page.goto(cobUrl);
|
||||
@@ -91,55 +91,3 @@ test("create a new issue", async ({ page, authenticatedPeer }) => {
|
||||
).toBeVisible();
|
||||
await expect(page.locator(".badge").filter({ hasText: "bug" })).toBeVisible();
|
||||
});
|
||||
|
||||
test("handling embeds", async ({ page, authenticatedPeer }) => {
|
||||
const { rid } = await createProject(authenticatedPeer, "embeds");
|
||||
await page.goto(
|
||||
`/nodes/${authenticatedPeer.httpdBaseUrl.hostname}:${authenticatedPeer.httpdBaseUrl.port}/${rid}/issues/new`,
|
||||
);
|
||||
await page.getByPlaceholder("Title").fill("This is a title");
|
||||
await page
|
||||
.getByPlaceholder("Write a description")
|
||||
.fill("Here is some text\n\n");
|
||||
await addEmbed(
|
||||
page,
|
||||
"./public/images/radicle-228x228.png",
|
||||
"radicle-228x228.png",
|
||||
"image/png",
|
||||
);
|
||||
await expect(page.getByPlaceholder("Write a description")).toHaveValue(
|
||||
"Here is some text\n\n\n",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Preview" }).click();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
"data:image/png;base64,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",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Submit" }).click();
|
||||
await expect(page.getByRole("button", { name: "Submit" })).toBeHidden();
|
||||
await expect(page.getByText("This is a title")).toBeVisible();
|
||||
await expect(page.getByText("Here is some text")).toBeVisible();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
const { scheme, hostname, port } = authenticatedPeer.httpdBaseUrl;
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
`${scheme}://${hostname}:${port}/raw/rad:z2J7s48EbCBckcEmj2dm5eaFVoBsy/blobs/bae036309c2182c7304c97956969369823b5c6ad?mime=image/png`,
|
||||
);
|
||||
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
});
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import { test } from "@tests/support/fixtures.js";
|
||||
import { test, expect } from "@tests/support/fixtures.js";
|
||||
import {
|
||||
addEmbed,
|
||||
createProject,
|
||||
expectReactionsToWork,
|
||||
expectThreadCommentingToWork,
|
||||
@@ -70,3 +71,95 @@ test("add and remove reactions", async ({ page, authenticatedPeer }) => {
|
||||
await page.goto(`${authenticatedPeer.uiUrl()}/${rid}/patches/${patchId}`);
|
||||
await expectReactionsToWork(page);
|
||||
});
|
||||
|
||||
test("handling embeds", async ({ page, authenticatedPeer }) => {
|
||||
const { rid, projectFolder } = await createProject(
|
||||
authenticatedPeer,
|
||||
"embeds",
|
||||
);
|
||||
await authenticatedPeer.rad(
|
||||
[
|
||||
"issue",
|
||||
"open",
|
||||
"--title",
|
||||
"This is an issue to handle embeds",
|
||||
"--description",
|
||||
"We'll give it a few comments and replies with embeds.",
|
||||
],
|
||||
{ cwd: projectFolder },
|
||||
);
|
||||
await page.goto(`${authenticatedPeer.uiUrl()}/${rid}/issues`);
|
||||
await page
|
||||
.getByRole("link", {
|
||||
name: "This is an issue to handle embeds",
|
||||
})
|
||||
.click();
|
||||
await page.getByRole("button", { name: "Leave your comment" }).click();
|
||||
|
||||
await page
|
||||
.getByPlaceholder("Leave your comment")
|
||||
.fill("Here is some text\n\n");
|
||||
await addEmbed(
|
||||
page,
|
||||
"./public/images/radicle-228x228.png",
|
||||
"radicle-228x228.png",
|
||||
"image/png",
|
||||
);
|
||||
await expect(page.getByPlaceholder("Leave your comment")).toHaveValue(
|
||||
"Here is some text\n\n\n",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Preview" }).click();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
"data:image/png;base64,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",
|
||||
);
|
||||
|
||||
await page.getByRole("button", { name: "Comment" }).click();
|
||||
await expect(page.getByPlaceholder("Leave your comment")).toBeHidden();
|
||||
await expect(page.getByText("Here is some text")).toBeVisible();
|
||||
await expect(
|
||||
page.getByRole("img", { name: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
const { scheme, hostname, port } = authenticatedPeer.httpdBaseUrl;
|
||||
expect(
|
||||
await page
|
||||
.getByRole("img", { name: "radicle-228x228.png" })
|
||||
.getAttribute("src"),
|
||||
).toBe(
|
||||
`${scheme}://${hostname}:${port}/raw/rad:z2J7s48EbCBckcEmj2dm5eaFVoBsy/blobs/bae036309c2182c7304c97956969369823b5c6ad?mime=image/png`,
|
||||
);
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
|
||||
await page.getByRole("button", { name: "edit comment" }).click();
|
||||
await page
|
||||
.getByPlaceholder("Leave your comment")
|
||||
.fill(
|
||||
"Here is some text\n\n\n\n",
|
||||
);
|
||||
await addEmbed(
|
||||
page,
|
||||
"./public/images/apple-touch-icon.png",
|
||||
"apple-touch-icon.png",
|
||||
"image/png",
|
||||
);
|
||||
await expect(page.getByPlaceholder("Leave your comment")).toHaveValue(
|
||||
"Here is some text\n\n\n\n\n",
|
||||
);
|
||||
await page.getByRole("button", { name: "Save" }).click();
|
||||
await expect(page.getByRole("button", { name: "Save" })).toBeHidden();
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "apple-touch-icon.png" }),
|
||||
).toBeVisible();
|
||||
await expect(
|
||||
page.locator(".badge").filter({ hasText: "radicle-228x228.png" }),
|
||||
).toBeVisible();
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user