Skip to content

Commit da7ccee

Browse files
authored
Diagram versioning (#560)
* clean up sidesheet * clean up sharing * add revisions sidesheet * update getCommits and clean up * update date localization * load diagram in read only mode from previous version * disable input from control panel and popovers * add restore warning modal * separate share and versions * update versions * finalize versioning implementation, add pagination * fix package-lock.json * clear versions cache on flush storgae * disable menubar items when in read only mode * disable remaining fields in readonlt * suppress eslint only-export-components rule * show loading version progress
1 parent 1eb4e29 commit da7ccee

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

42 files changed

+3235
-1729
lines changed

.eslintrc.cjs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ module.exports = {
66
"plugin:react/recommended",
77
"plugin:react/jsx-runtime",
88
"plugin:react-hooks/recommended",
9-
"prettier"
9+
"prettier",
1010
],
1111
ignorePatterns: ["dist", ".eslintrc.cjs"],
1212
parserOptions: { ecmaVersion: "latest", sourceType: "module" },
@@ -18,5 +18,6 @@ module.exports = {
1818
{ allowConstantExport: true },
1919
],
2020
"react/prop-types": 0,
21+
"react-refresh/only-export-components": "off",
2122
},
2223
};

package-lock.json

Lines changed: 2435 additions & 1566 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
{
2-
"name": "client-vite",
2+
"name": "drawdb",
33
"private": true,
44
"version": "0.0.0",
55
"type": "module",
@@ -32,6 +32,8 @@
3232
"jspdf": "^3.0.1",
3333
"jszip": "^3.10.1",
3434
"lexical": "^0.12.5",
35+
"lodash": "^4.17.21",
36+
"luxon": "^3.7.1",
3537
"nanoid": "^5.1.5",
3638
"node-sql-parser": "^5.3.11",
3739
"oracle-sql-parser": "^0.1.0",

src/api/gists.js

Lines changed: 44 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import axios from "axios";
22

3-
const filename = "share.json";
4-
const description = "drawDB diagram";
3+
export const SHARE_FILENAME = "share.json";
4+
export const VERSION_FILENAME = "versionned.json";
55

6+
const description = "drawDB diagram";
67
const baseUrl = import.meta.env.VITE_BACKEND_URL;
78

8-
export async function create(content) {
9+
export async function create(filename, content) {
910
const res = await axios.post(`${baseUrl}/gists`, {
1011
public: false,
1112
filename,
@@ -16,11 +17,13 @@ export async function create(content) {
1617
return res.data.data.id;
1718
}
1819

19-
export async function patch(gistId, content) {
20-
await axios.patch(`${baseUrl}/gists/${gistId}`, {
20+
export async function patch(gistId, filename, content) {
21+
const { deleted } = await axios.patch(`${baseUrl}/gists/${gistId}`, {
2122
filename,
2223
content,
2324
});
25+
26+
return deleted;
2427
}
2528

2629
export async function del(gistId) {
@@ -32,3 +35,39 @@ export async function get(gistId) {
3235

3336
return res.data;
3437
}
38+
39+
export async function getCommits(gistId, perPage = 20, page = 1) {
40+
const res = await axios.get(`${baseUrl}/gists/${gistId}/commits`, {
41+
params: {
42+
per_page: perPage,
43+
page,
44+
},
45+
});
46+
47+
return res.data;
48+
}
49+
50+
export async function getVersion(gistId, sha) {
51+
const res = await axios.get(`${baseUrl}/gists/${gistId}/${sha}`);
52+
53+
return res.data;
54+
}
55+
56+
export async function getCommitsWithFile(
57+
gistId,
58+
file,
59+
limit = 10,
60+
cursor = null,
61+
) {
62+
const res = await axios.get(
63+
`${baseUrl}/gists/${gistId}/file-versions/${file}`,
64+
{
65+
params: {
66+
limit,
67+
cursor,
68+
},
69+
},
70+
);
71+
72+
return res.data;
73+
}

src/assets/calendar.png

-11.9 KB
Binary file not shown.

src/assets/process.png

-22.9 KB
Binary file not shown.

src/assets/process_dark.png

-18.4 KB
Binary file not shown.

src/components/EditorCanvas/Area.jsx

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -179,6 +179,7 @@ export default function Area({
179179
backgroundColor: "#2F68ADB3",
180180
}}
181181
onClick={lockUnlockArea}
182+
disabled={layout.readOnly}
182183
/>
183184
<Popover
184185
visible={areaIsOpen() && !layout.sidebar}
@@ -257,6 +258,7 @@ function EditPopoverContent({ data }) {
257258
const { updateArea, deleteArea } = useAreas();
258259
const { setUndoStack, setRedoStack } = useUndoRedo();
259260
const { t } = useTranslation();
261+
const { layout } = useLayout();
260262
const initialColorRef = useRef(data.color);
261263

262264
const handleColorPick = (color) => {
@@ -302,6 +304,7 @@ function EditPopoverContent({ data }) {
302304
value={data.name}
303305
placeholder={t("name")}
304306
className="me-2"
307+
readonly={layout.readOnly}
305308
onChange={(value) => updateArea(data.id, { name: value })}
306309
onFocus={(e) => setEditField({ name: e.target.value })}
307310
onBlur={(e) => {
@@ -325,6 +328,7 @@ function EditPopoverContent({ data }) {
325328
/>
326329
<ColorPicker
327330
usePopover={true}
331+
readOnly={layout.readOnly}
328332
value={data.color}
329333
onChange={(color) => updateArea(data.id, { color })}
330334
onColorPick={(color) => handleColorPick(color)}
@@ -336,6 +340,7 @@ function EditPopoverContent({ data }) {
336340
type="danger"
337341
block
338342
onClick={() => deleteArea(data.id, true)}
343+
disabled={layout.readOnly}
339344
>
340345
{t("delete")}
341346
</Button>

src/components/EditorCanvas/Canvas.jsx

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -279,21 +279,24 @@ export default function Canvas() {
279279

280280
if (!e.isPrimary) return;
281281

282+
282283
if (panning.isPanning) {
283284
setTransform((prev) => ({
284285
...prev,
285286
pan: {
286287
x:
287-
panning.panStart.x +
288-
(panning.cursorStart.x - pointer.spaces.screen.x) / transform.zoom,
288+
panning.panStart.x +
289+
(panning.cursorStart.x - pointer.spaces.screen.x) / transform.zoom,
289290
y:
290-
panning.panStart.y +
291-
(panning.cursorStart.y - pointer.spaces.screen.y) / transform.zoom,
291+
panning.panStart.y +
292+
(panning.cursorStart.y - pointer.spaces.screen.y) / transform.zoom,
292293
},
293294
}));
294295
return;
295296
}
296297

298+
if(layout.readOnly) return;
299+
297300
if (linking) {
298301
setLinkingLine({
299302
...linkingLine,

src/components/EditorCanvas/Note.jsx

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -249,6 +249,7 @@ export default function Note({ data, onPointerDown }) {
249249
backgroundColor: "#2F68ADB3",
250250
}}
251251
onClick={lockUnlockNote}
252+
disabled={layout.readOnly}
252253
/>
253254
<Popover
254255
visible={
@@ -280,6 +281,7 @@ export default function Note({ data, onPointerDown }) {
280281
value={data.title}
281282
placeholder={t("title")}
282283
className="me-2"
284+
readonly={layout.readOnly}
283285
onChange={(value) =>
284286
updateNote(data.id, { title: value })
285287
}
@@ -307,16 +309,18 @@ export default function Note({ data, onPointerDown }) {
307309
/>
308310
<ColorPicker
309311
usePopover={true}
312+
readOnly={layout.readOnly}
310313
value={data.color}
311314
onChange={(color) => updateNote(data.id, { color })}
312315
onColorPick={(color) => handleColorPick(color)}
313316
/>
314317
</div>
315318
<div className="flex">
316319
<Button
317-
icon={<IconDeleteStroked />}
318-
type="danger"
319320
block
321+
type="danger"
322+
disabled={layout.readOnly}
323+
icon={<IconDeleteStroked />}
320324
onClick={() => deleteNote(data.id, true)}
321325
>
322326
{t("delete")}
@@ -343,6 +347,7 @@ export default function Note({ data, onPointerDown }) {
343347
</div>
344348
<textarea
345349
id={`note_${data.id}`}
350+
readOnly={layout.readOnly}
346351
value={data.content}
347352
onChange={handleChange}
348353
onFocus={(e) =>

0 commit comments

Comments
 (0)