Added list feature.
This commit is contained in:
parent
73a3aa6ac9
commit
abffa90506
|
@ -7,6 +7,8 @@ services:
|
||||||
image: mongo
|
image: mongo
|
||||||
volumes:
|
volumes:
|
||||||
- ./mongo:/data/db
|
- ./mongo:/data/db
|
||||||
|
ports:
|
||||||
|
- 27017:27017
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
|
|
||||||
link-warden-api:
|
link-warden-api:
|
||||||
|
|
|
@ -7,6 +7,7 @@ import Filters from "./componets/Filters";
|
||||||
import sortList from "./modules/sortList";
|
import sortList from "./modules/sortList";
|
||||||
import filter from "./modules/filterData";
|
import filter from "./modules/filterData";
|
||||||
import concatTags from "./modules/concatTags";
|
import concatTags from "./modules/concatTags";
|
||||||
|
import concatLists from "./modules/concatLists";
|
||||||
import NoResults from "./componets/NoResults";
|
import NoResults from "./componets/NoResults";
|
||||||
import Loader from "./componets/Loader";
|
import Loader from "./componets/Loader";
|
||||||
import SideBar from "./componets/SideBar";
|
import SideBar from "./componets/SideBar";
|
||||||
|
@ -59,6 +60,8 @@ function App() {
|
||||||
|
|
||||||
const tags = concatTags(data);
|
const tags = concatTags(data);
|
||||||
|
|
||||||
|
const lists = concatLists(data);
|
||||||
|
|
||||||
async function fetchData() {
|
async function fetchData() {
|
||||||
const res = await fetch(API_HOST + "/api");
|
const res = await fetch(API_HOST + "/api");
|
||||||
const resJSON = await res.json();
|
const resJSON = await res.json();
|
||||||
|
@ -153,6 +156,7 @@ function App() {
|
||||||
reFetch={fetchData}
|
reFetch={fetchData}
|
||||||
lightMode={lightMode}
|
lightMode={lightMode}
|
||||||
tags={() => tags}
|
tags={() => tags}
|
||||||
|
lists={() => lists}
|
||||||
/>
|
/>
|
||||||
) : null}
|
) : null}
|
||||||
|
|
||||||
|
@ -171,6 +175,7 @@ function App() {
|
||||||
SetLoader={SetLoader}
|
SetLoader={SetLoader}
|
||||||
data={filteredData}
|
data={filteredData}
|
||||||
tags={tags}
|
tags={tags}
|
||||||
|
lists={lists}
|
||||||
reFetch={fetchData}
|
reFetch={fetchData}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -2,15 +2,17 @@ import { useState } from "react";
|
||||||
import "../styles/SendItem.css";
|
import "../styles/SendItem.css";
|
||||||
import TagSelection from "./TagSelection";
|
import TagSelection from "./TagSelection";
|
||||||
import addItem from "../modules/send";
|
import addItem from "../modules/send";
|
||||||
|
import ListSelection from "./ListSelection";
|
||||||
|
|
||||||
const AddItem = ({ onExit, reFetch, tags, SetLoader, lightMode }) => {
|
const AddItem = ({ onExit, reFetch, tags, lists, SetLoader, lightMode }) => {
|
||||||
const [name, setName] = useState("");
|
const [name, setName] = useState(""),
|
||||||
const [link, setLink] = useState("");
|
[link, setLink] = useState(""),
|
||||||
const [tag, setTag] = useState([]);
|
[tag, setTag] = useState([]),
|
||||||
|
[list, setList] = useState([]);
|
||||||
|
|
||||||
function newItem() {
|
function newItem() {
|
||||||
SetLoader(true);
|
SetLoader(true);
|
||||||
addItem(name, link, tag, reFetch, onExit, SetLoader, "POST");
|
addItem(name, link, tag, list, reFetch, onExit, SetLoader, "POST");
|
||||||
}
|
}
|
||||||
|
|
||||||
function SetName(e) {
|
function SetName(e) {
|
||||||
|
@ -22,10 +24,13 @@ const AddItem = ({ onExit, reFetch, tags, SetLoader, lightMode }) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
function SetTags(value) {
|
function SetTags(value) {
|
||||||
setTag(value);
|
|
||||||
setTag(value.map((e) => e.value.toLowerCase()));
|
setTag(value.map((e) => e.value.toLowerCase()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function SetList(value) {
|
||||||
|
setList(value.value);
|
||||||
|
}
|
||||||
|
|
||||||
function abort(e) {
|
function abort(e) {
|
||||||
if (e.target.className === "add-overlay") {
|
if (e.target.className === "add-overlay") {
|
||||||
onExit();
|
onExit();
|
||||||
|
@ -61,6 +66,14 @@ const AddItem = ({ onExit, reFetch, tags, SetLoader, lightMode }) => {
|
||||||
Tags: <span className="optional">(Optional)</span>
|
Tags: <span className="optional">(Optional)</span>
|
||||||
</h3>
|
</h3>
|
||||||
<TagSelection setTags={SetTags} tags={tags} lightMode={lightMode} />
|
<TagSelection setTags={SetTags} tags={tags} lightMode={lightMode} />
|
||||||
|
<h3>
|
||||||
|
List: <span className="optional">(Optional)</span>
|
||||||
|
</h3>
|
||||||
|
<ListSelection
|
||||||
|
setList={SetList}
|
||||||
|
lists={lists}
|
||||||
|
lightMode={lightMode}
|
||||||
|
/>
|
||||||
<button onClick={newItem} className="send-btn">
|
<button onClick={newItem} className="send-btn">
|
||||||
Add 
|
Add 
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -3,10 +3,12 @@ import deleteEntity from "../modules/deleteEntity";
|
||||||
import "../styles/SendItem.css";
|
import "../styles/SendItem.css";
|
||||||
import TagSelection from "./TagSelection";
|
import TagSelection from "./TagSelection";
|
||||||
import editItem from "../modules/send";
|
import editItem from "../modules/send";
|
||||||
|
import ListSelection from "./ListSelection";
|
||||||
|
|
||||||
const EditItem = ({ tags, item, onExit, SetLoader, reFetch, lightMode }) => {
|
const EditItem = ({ tags, lists, item, onExit, SetLoader, reFetch, lightMode }) => {
|
||||||
const [name, setName] = useState(item.name);
|
const [name, setName] = useState(item.name),
|
||||||
const [tag, setTag] = useState(item.tag);
|
[tag, setTag] = useState(item.tag),
|
||||||
|
[list, setList] = useState(item.list);
|
||||||
|
|
||||||
function EditItem() {
|
function EditItem() {
|
||||||
SetLoader(true);
|
SetLoader(true);
|
||||||
|
@ -14,6 +16,7 @@ const EditItem = ({ tags, item, onExit, SetLoader, reFetch, lightMode }) => {
|
||||||
name,
|
name,
|
||||||
item.link,
|
item.link,
|
||||||
tag,
|
tag,
|
||||||
|
list,
|
||||||
reFetch,
|
reFetch,
|
||||||
onExit,
|
onExit,
|
||||||
SetLoader,
|
SetLoader,
|
||||||
|
@ -33,10 +36,13 @@ const EditItem = ({ tags, item, onExit, SetLoader, reFetch, lightMode }) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
function SetTags(value) {
|
function SetTags(value) {
|
||||||
setTag(value);
|
|
||||||
setTag(value.map((e) => e.value.toLowerCase()));
|
setTag(value.map((e) => e.value.toLowerCase()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function SetList(value) {
|
||||||
|
setList(value.value);
|
||||||
|
}
|
||||||
|
|
||||||
function abort(e) {
|
function abort(e) {
|
||||||
if (e.target.className === "add-overlay") {
|
if (e.target.className === "add-overlay") {
|
||||||
onExit();
|
onExit();
|
||||||
|
@ -89,6 +95,15 @@ const EditItem = ({ tags, item, onExit, SetLoader, reFetch, lightMode }) => {
|
||||||
tag={tag}
|
tag={tag}
|
||||||
lightMode={lightMode}
|
lightMode={lightMode}
|
||||||
/>
|
/>
|
||||||
|
<h3>
|
||||||
|
List: <span className="optional">(Optional)</span>
|
||||||
|
</h3>
|
||||||
|
<ListSelection
|
||||||
|
setList={SetList}
|
||||||
|
lists={lists}
|
||||||
|
list={list}
|
||||||
|
lightMode={lightMode}
|
||||||
|
/>
|
||||||
<button onClick={EditItem} className="send-btn">
|
<button onClick={EditItem} className="send-btn">
|
||||||
Update 
|
Update 
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -5,7 +5,7 @@ import EditItem from "./EditItem";
|
||||||
import { useState } from "react";
|
import { useState } from "react";
|
||||||
import { Link } from "react-router-dom";
|
import { Link } from "react-router-dom";
|
||||||
|
|
||||||
const List = ({ data, tags, reFetch, SetLoader, lightMode }) => {
|
const List = ({ data, tags, lists, reFetch, SetLoader, lightMode }) => {
|
||||||
const [editBox, setEditBox] = useState(false);
|
const [editBox, setEditBox] = useState(false);
|
||||||
const [editIndex, setEditIndex] = useState(0);
|
const [editIndex, setEditIndex] = useState(0);
|
||||||
|
|
||||||
|
@ -24,6 +24,7 @@ const List = ({ data, tags, reFetch, SetLoader, lightMode }) => {
|
||||||
<EditItem
|
<EditItem
|
||||||
lightMode={lightMode}
|
lightMode={lightMode}
|
||||||
tags={() => tags}
|
tags={() => tags}
|
||||||
|
lists={() => lists}
|
||||||
onExit={exitEditing}
|
onExit={exitEditing}
|
||||||
SetLoader={SetLoader}
|
SetLoader={SetLoader}
|
||||||
reFetch={reFetch}
|
reFetch={reFetch}
|
||||||
|
|
|
@ -0,0 +1,63 @@
|
||||||
|
import CreatableSelect from "react-select/creatable";
|
||||||
|
|
||||||
|
export default function ListSelection({ setList, lists, list = 'Unsorted', lightMode }) {
|
||||||
|
const customStyles = {
|
||||||
|
container: (provided) => ({
|
||||||
|
...provided,
|
||||||
|
textShadow: "none",
|
||||||
|
}),
|
||||||
|
|
||||||
|
placeholder: (provided) => ({
|
||||||
|
...provided,
|
||||||
|
color: "#a9a9a9",
|
||||||
|
}),
|
||||||
|
|
||||||
|
menu: (provided) => ({
|
||||||
|
...provided,
|
||||||
|
border: "solid",
|
||||||
|
borderWidth: "1px",
|
||||||
|
borderRadius: "0px",
|
||||||
|
borderColor: "rgb(141, 141, 141)",
|
||||||
|
opacity: "90%",
|
||||||
|
color: "gray",
|
||||||
|
background: lightMode ? "lightyellow" : "#273949",
|
||||||
|
boxShadow:
|
||||||
|
"rgba(0, 0, 0, 0.16) 0px 3px 6px, rgba(0, 0, 0, 0.23) 0px 3px 6px",
|
||||||
|
}),
|
||||||
|
|
||||||
|
input: (provided) => ({
|
||||||
|
...provided,
|
||||||
|
color: lightMode ? "rgb(64, 64, 64)" : "white",
|
||||||
|
}),
|
||||||
|
|
||||||
|
singleValue: (provided) => ({
|
||||||
|
...provided,
|
||||||
|
color: lightMode ? "rgb(64, 64, 64)" : "white",
|
||||||
|
}),
|
||||||
|
|
||||||
|
control: (provided, state) => ({
|
||||||
|
...provided,
|
||||||
|
background: lightMode ? "lightyellow" : "#273949",
|
||||||
|
border: "none",
|
||||||
|
borderRadius: "0px",
|
||||||
|
boxShadow: state.isFocused
|
||||||
|
? "rgba(0, 0, 0, 0.16) 0px 3px 6px, rgba(0, 0, 0, 0.23) 0px 3px 6px"
|
||||||
|
: "rgba(0, 0, 0, 0.4) 0px 2px 4px, rgba(0, 0, 0, 0.3) 0px 7px 13px -3px, rgba(0, 0, 0, 0.2) 0px -3px 0px inset",
|
||||||
|
}),
|
||||||
|
};
|
||||||
|
|
||||||
|
const data = lists().map((e) => {
|
||||||
|
return { value: e, label: e };
|
||||||
|
});
|
||||||
|
|
||||||
|
const defaultList = { value: list, label: list };
|
||||||
|
|
||||||
|
return (
|
||||||
|
<CreatableSelect
|
||||||
|
defaultValue={defaultList}
|
||||||
|
styles={customStyles}
|
||||||
|
onChange={setList}
|
||||||
|
options={data}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
|
@ -1,6 +1,5 @@
|
||||||
import CreatableSelect from "react-select/creatable";
|
import CreatableSelect from "react-select/creatable";
|
||||||
|
|
||||||
// lightMode ? "Black" : "White"
|
|
||||||
export default function TagSelection({ setTags, tags, tag = [], lightMode }) {
|
export default function TagSelection({ setTags, tags, tag = [], lightMode }) {
|
||||||
const customStyles = {
|
const customStyles = {
|
||||||
container: (provided) => ({
|
container: (provided) => ({
|
||||||
|
@ -18,11 +17,6 @@ export default function TagSelection({ setTags, tags, tag = [], lightMode }) {
|
||||||
color: "gray",
|
color: "gray",
|
||||||
}),
|
}),
|
||||||
|
|
||||||
indicatorSeparator: (provided) => ({
|
|
||||||
...provided,
|
|
||||||
display: "none",
|
|
||||||
}),
|
|
||||||
|
|
||||||
menu: (provided) => ({
|
menu: (provided) => ({
|
||||||
...provided,
|
...provided,
|
||||||
border: "solid",
|
border: "solid",
|
||||||
|
|
|
@ -0,0 +1,13 @@
|
||||||
|
const concatLists = (data) => {
|
||||||
|
let lists = [];
|
||||||
|
|
||||||
|
for (let i = 0; i < data.length; i++) {
|
||||||
|
lists = lists.concat(data[i].list);
|
||||||
|
}
|
||||||
|
|
||||||
|
lists = lists.filter((v, i, a) => a.indexOf(v) === i);
|
||||||
|
|
||||||
|
return lists;
|
||||||
|
};
|
||||||
|
|
||||||
|
export default concatLists;
|
|
@ -5,6 +5,7 @@ const addItem = async (
|
||||||
name,
|
name,
|
||||||
link,
|
link,
|
||||||
tag,
|
tag,
|
||||||
|
list,
|
||||||
reFetch,
|
reFetch,
|
||||||
onExit,
|
onExit,
|
||||||
SetLoader,
|
SetLoader,
|
||||||
|
@ -36,6 +37,7 @@ const addItem = async (
|
||||||
title: title,
|
title: title,
|
||||||
link: link,
|
link: link,
|
||||||
tag: tag,
|
tag: tag,
|
||||||
|
list: list,
|
||||||
date: dateCreated,
|
date: dateCreated,
|
||||||
}),
|
}),
|
||||||
headers: {
|
headers: {
|
||||||
|
|
Ŝarĝante…
Reference in New Issue