Skip to content

Commit

Permalink
Rajat1saxena/issue462 (#464)
Browse files Browse the repository at this point in the history
* WIP: Removed unnecessary media related permissions

* Refactoring

* WIP: Checks to ensure ownership and access before media deletion

* Lint fixes

* New profile design; Tested delete media role-based access; UI enhancements

* All media now gets saved at soon as it is uploaded on MediaLit

---------

Co-authored-by: Rajat Saxena <[email protected]>
  • Loading branch information
rajat1saxena and Rajat Saxena authored Aug 9, 2024
1 parent 2b416ab commit ace1a66
Show file tree
Hide file tree
Showing 35 changed files with 987 additions and 649 deletions.
2 changes: 1 addition & 1 deletion SECURITY.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,4 @@ Use the application at your own risk. People who have worked on this project wil

## Reporting a vulnerability

Please drop a mail at [hi@sub.rajatsaxena.dev](mailto:hi@sub.rajatsaxena.dev) or tweet at [@CourseLit](https://twitter.com/courselit). We will try to address it as soon as possible.
Please drop a mail at [hi@codelit.dev](mailto:hi@codelit.dev) or tweet at [@CourseLit](https://twitter.com/courselit). We will try to address it as soon as possible.
12 changes: 0 additions & 12 deletions apps/docs/src/pages/en/users/permissions.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,22 +44,10 @@ Let take a moment to understand what all permissions are available and what aspe

Access/update school's users.

- **View files**

Access school's files like images, videos, PDFs etc.

- **Upload files**

Upload media assets like images, videos, PDFs etc.

- **Manage files**

Update/delete your media assets

- **Manage all files**

Update/delete any media asset. This includes media uploaded by other creators in the school.

## Stuck somewhere?

We are always here for you. Come chat with us in our <a href="https://discord.com/invite/GR4bQsN" target="_blank">Discord</a> channel or send a tweet at <a href="https://twitter.com/courselit" target="_blank">@CourseLit</a>.
109 changes: 68 additions & 41 deletions apps/web/components/admin/blogs/editor/details.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import {
Form,
FormField,
Button,
PageBuilderPropertyHeader,
} from "@courselit/components-library";
import useCourse from "./course-hook";
import { FetchBuilder } from "@courselit/utils";
Expand All @@ -18,6 +19,7 @@ import { Address, AppMessage, Auth, Profile } from "@courselit/common-models";
import {
APP_MESSAGE_COURSE_SAVED,
BUTTON_SAVE,
COURSE_CONTENT_HEADER,
FORM_FIELD_FEATURED_IMAGE,
} from "../../../../ui-config/strings";
import { connect } from "react-redux";
Expand Down Expand Up @@ -61,27 +63,7 @@ function Details({ id, address, dispatch, auth, profile }: DetailsProps) {
updateCourse(courseData: {
id: "${course!.id}"
title: "${title}",
description: ${JSON.stringify(JSON.stringify(description))},
featuredImage: ${
featuredImage.mediaId
? `{
mediaId: "${featuredImage.mediaId}",
originalFileName: "${
featuredImage.originalFileName
}",
mimeType: "${featuredImage.mimeType}",
size: ${featuredImage.size},
access: "${featuredImage.access}",
file: ${
featuredImage.access === "public"
? `"${featuredImage.file}"`
: null
},
thumbnail: "${featuredImage.thumbnail}",
caption: "${featuredImage.caption}"
}`
: null
}
description: ${JSON.stringify(JSON.stringify(description))}
}) {
id
}
Expand All @@ -107,22 +89,67 @@ function Details({ id, address, dispatch, auth, profile }: DetailsProps) {
}
};

const saveFeaturedImage = async (media?: Media) => {
const mutation = `
mutation ($courseId: ID!, $media: MediaInput) {
updateCourse(courseData: {
id: $courseId
featuredImage: $media
}) {
id
}
}
`;
const fetch = new FetchBuilder()
.setUrl(`${address.backend}/api/graph`)
.setPayload({
query: mutation,
variables: {
courseId: course?.id,
media: media || null,
},
})
.setIsGraphQLEndpoint(true)
.build();
try {
dispatch(networkAction(true));
const response = await fetch.exec();
if (response.updateCourse) {
dispatch(
setAppMessage(new AppMessage(APP_MESSAGE_COURSE_SAVED)),
);
}
} catch (err: any) {
dispatch(setAppMessage(new AppMessage(err.message)));
} finally {
dispatch(networkAction(false));
}
};

return (
<Section>
<Form onSubmit={updateDetails} className="flex flex-col gap-4">
<FormField
required
label="Title"
name="title"
value={title}
onChange={(e) => setTitle(e.target.value)}
/>
<TextEditor
initialContent={description}
refresh={refreshDetails}
onChange={(state: any) => setDescription(state)}
url={address.backend}
/>
<div className="flex flex-col gap-4">
<Section>
<Form onSubmit={updateDetails} className="flex flex-col gap-4">
<FormField
required
label="Title"
name="title"
value={title}
onChange={(e) => setTitle(e.target.value)}
/>
<PageBuilderPropertyHeader label={COURSE_CONTENT_HEADER} />
<TextEditor
initialContent={description}
refresh={refreshDetails}
onChange={(state: any) => setDescription(state)}
url={address.backend}
/>
<div>
<Button type="submit">{BUTTON_SAVE}</Button>
</div>
</Form>
</Section>
<Section>
<MediaSelector
title={FORM_FIELD_FEATURED_IMAGE}
src={(featuredImage && featuredImage.thumbnail) || ""}
Expand All @@ -131,6 +158,7 @@ function Details({ id, address, dispatch, auth, profile }: DetailsProps) {
}
onSelection={(media?: Media) => {
media && setFeaturedImage(media);
saveFeaturedImage(media);
}}
mimeTypesToShow={[...MIMETYPE_IMAGE]}
access="public"
Expand All @@ -142,13 +170,12 @@ function Details({ id, address, dispatch, auth, profile }: DetailsProps) {
mediaId={(featuredImage && featuredImage.mediaId) || ""}
onRemove={() => {
setFeaturedImage({});
saveFeaturedImage();
}}
type="course"
/>
<div>
<Button type="submit">{BUTTON_SAVE}</Button>
</div>
</Form>
</Section>
</Section>
</div>
);
}

Expand Down
4 changes: 2 additions & 2 deletions apps/web/components/admin/dashboard/to-do.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ const Todo = ({ siteinfo }) => {
{(!siteinfo.title || (siteinfo.logo && !siteinfo.logo.file)) && (
<div className="flex flex-col border border-red-200 p-2 rounded-lg">
<h2 className="font-semibold mb-1">
Basic details missing
Basic details missing 💁‍♀️
</h2>
<p className="text-sm text-slate-500 mb-4">
Give your school a proper name, description and a logo.
Expand All @@ -35,7 +35,7 @@ const Todo = ({ siteinfo }) => {
)}
{(!siteinfo.currencyISOCode || !siteinfo.paymentMethod) && (
<div className="flex flex-col border border-red-200 p-2 rounded-lg">
<h2 className="font-semibold mb-1">Start earning</h2>
<h2 className="font-semibold mb-1">Start earning 💸</h2>
<p className="text-sm text-slate-500 mb-4">
Update your payment details to sell paid products.
</p>
Expand Down
6 changes: 2 additions & 4 deletions apps/web/components/admin/page-editor/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -352,7 +352,7 @@ function PageEditor({
layout?: Record<string, unknown>[];
title?: string;
description?: string;
socialImage?: Media | {};
socialImage?: Media | null;
robotsAllowed?: boolean;
}) => {
if (!pageId) {
Expand Down Expand Up @@ -573,9 +573,7 @@ function PageEditor({
? page.robotsAllowed
: true
}
socialImage={
page.draftSocialImage || page.socialImage || {}
}
socialImage={page.draftSocialImage || {}}
onClose={(e) => setLeftPaneContent("none")}
onSave={({
title,
Expand Down
56 changes: 30 additions & 26 deletions apps/web/components/admin/page-editor/seo-editor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -90,32 +90,6 @@ function SeoEditor({
setInnerDescription(e.target.value)
}
/>
<PageBuilderPropertyHeader
label={SEO_FORM_SOCIAL_IMAGE_LABEL}
tooltip={SEO_FORM_SOCIAL_IMAGE_TOOLTIP}
/>
<MediaSelector
title=""
src={innerSocialImage && innerSocialImage.thumbnail}
srcTitle={
innerSocialImage && innerSocialImage.originalFileName
}
dispatch={dispatch}
auth={auth}
profile={profile}
address={address}
onSelection={(media: Media) => {
if (media) {
setInnerSocialImage(media);
}
}}
onRemove={() => {
setInnerSocialImage({});
}}
strings={{}}
access="public"
mediaId={innerSocialImage && innerSocialImage.mediaId}
/>
<div className="flex justify-between">
<PageBuilderPropertyHeader label={SEO_FORM_ROBOTS_LABEL} />
<Checkbox
Expand All @@ -139,6 +113,36 @@ function SeoEditor({
/>
</div>
</Form>
<div className="p-2">
<MediaSelector
title={SEO_FORM_SOCIAL_IMAGE_LABEL}
tooltip={SEO_FORM_SOCIAL_IMAGE_TOOLTIP}
src={(innerSocialImage && innerSocialImage.thumbnail) || ""}
srcTitle={
(innerSocialImage &&
innerSocialImage.originalFileName) ||
""
}
dispatch={dispatch}
auth={auth}
profile={profile}
address={address}
onSelection={(media: Media) => {
if (media) {
setInnerSocialImage(media);
onSave({ socialImage: media });
}
}}
onRemove={() => {
setInnerSocialImage({});
onSave({ socialImage: null });
}}
strings={{}}
access="public"
mediaId={innerSocialImage && innerSocialImage.mediaId}
type="page"
/>
</div>
</div>
);
}
Expand Down
Loading

0 comments on commit ace1a66

Please sign in to comment.