Skip to content

Commit

Permalink
Drag & drop proof of concept E2E
Browse files Browse the repository at this point in the history
- native dnd is still problematic
- uses injected script for simulating dnd
  • Loading branch information
mtsgrd committed Sep 2, 2024
1 parent 1792255 commit 29b2b6b
Show file tree
Hide file tree
Showing 13 changed files with 190 additions and 46 deletions.
11 changes: 11 additions & 0 deletions apps/desktop/e2e/scripts/confirm-analytics.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#!/usr/bin/env bash

set -eu -o pipefail

DATA_DIR="$HOME/.local/share/com.gitbutler.app.dev"
if [ ! -d "$DATA_DIR" ]; then
echo "Creating data dir: $DATA_DIR"
mkdir -p $DATA_DIR
fi
echo "Confirming analytics"
echo '{"appAnalyticsConfirmed":true}' > $DATA_DIR/settings.json
47 changes: 47 additions & 0 deletions apps/desktop/e2e/scripts/init.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
#!/usr/bin/env bash

set -eu -o pipefail

TEMP_DIR=${1:?The first argument is a temp dir}
# Convert to absolute path
TEMP_DIR=$(realpath "$TEMP_DIR")


CLI=$(realpath "../../target/debug/gitbutler-cli")

DATA_DIR="$HOME/.local/share/com.gitbutler.app.dev"
if [ -d "$DATA_DIR" ]; then
rm -rf $DATA_DIR
fi

function setGitDefaults() {
git config user.email "[email protected]"
git config user.name "Test User"
git config init.defaultBranch master
}

function tick() {
if test -z "${tick+set}"; then
tick=1675176957
else
tick=$($tick + 60)
fi
GIT_COMMITTER_DATE="$tick +0100"
GIT_AUTHOR_DATE="$tick +0100"
export GIT_COMMITTER_DATE GIT_AUTHOR_DATE
}
tick

if [ -d "$TEMP_DIR" ]; then
rm -rf "$TEMP_DIR"
fi
mkdir "$TEMP_DIR"

(
cd "$TEMP_DIR"
git init remote
cd remote
setGitDefaults
echo first >file
git add . && git commit -m "init"
)
24 changes: 16 additions & 8 deletions apps/desktop/e2e/tests/add-project.spec.ts
Original file line number Diff line number Diff line change
@@ -1,24 +1,32 @@
import { spawnAndLog, findAndClick, setElementValue } from '../utils.js';
import { spawnAndLog, findAndClick, setElementValue } from '../utils';

const TEMP_DIR = '/tmp/gitbutler-add-project';
const REPO_NAME = 'one-vbranch-on-integration';

describe('Project', () => {
before(() => {
spawnAndLog('bash', [
'-c',
'./e2e/scripts/init-repositories.sh ../../target/debug/gitbutler-cli'
`
source ./e2e/scripts/init.sh ${TEMP_DIR}
cd ${TEMP_DIR};
git clone remote ${REPO_NAME} && cd ${REPO_NAME}
$CLI project -s dev add --switch-to-integration "$(git rev-parse --symbolic-full-name "@{u}")"
$CLI branch create virtual
`
]);
});

it('should add a local project', async () => {
await findAndClick('button[data-testid="analytics-continue"]');

const dirInput = await $('input[data-testid="test-directory-path"]');
setElementValue(dirInput, '/tmp/gb-e2e-repos/one-vbranch-on-integration');
setElementValue(dirInput, `${TEMP_DIR}/${REPO_NAME}`);

await findAndClick('button[data-testid="add-local-project"]');
await findAndClick('button[data-testid="set-base-branch"]');
await findAndClick('button[data-testid="accept-git-auth"]');
await $('button[data-testid="add-local-project"]').then(async (b) => await b.click());
await $('button[data-testid="set-base-branch"]').then(async (b) => await b.click());
await $('button[data-testid="accept-git-auth"]').then(async (b) => await b.click());

const workspaceButton = await $('button=Workspace');
await expect(workspaceButton).toExist();
await expect($('button=Workspace')).toExist();
});
});
38 changes: 38 additions & 0 deletions apps/desktop/e2e/tests/drag-file.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import { spawnAndLog } from '../utils';
import { codeForSelectors as dragAndDrop } from 'html-dnd';

const TEMP_DIR = '/tmp/gitbutler-drag-files';
const REPO_NAME = 'simple-drag-test';

describe('Drag', () => {
before(() => {
spawnAndLog('bash', [
'-c',
`
source ./e2e/scripts/init.sh ${TEMP_DIR}
bash ./e2e/scripts/confirm-analytics.sh
cd ${TEMP_DIR};
git clone remote ${REPO_NAME} && cd ${REPO_NAME}
$CLI project -s dev add --switch-to-integration "$(git rev-parse --symbolic-full-name "@{u}")"
$CLI branch create virtual-one
$CLI branch create virtual-two
echo "hello world" > hello
`
]);
});

it('drag file from one lane to another', async () => {
const fileSelector = '[data-testid="file-helloworld.txt"]';
const dropSelector = '[data-testid="virtual-two-files-dz"]';

const fileItem = await $(fileSelector);
const dropTarget = await $(dropSelector);
await fileItem.waitForDisplayed();
await dropTarget.waitForDisplayed();

// The actual drop target can be different from the element with the `dropZone` directive..
await driver.executeScript(dragAndDrop, [fileSelector, dropSelector + ' .dropzone-target']);

await expect('[data-testid="branch-virtual-two"] [data-testid="file-hello"]').toBeDisplayed();
});
});
1 change: 1 addition & 0 deletions apps/desktop/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@
"diff-match-patch": "^1.0.5",
"fuse.js": "^7.0.0",
"git-url-parse": "^14.0.0",
"html-dnd": "^1.2.1",
"jsdom": "^24.1.1",
"lscache": "^1.3.2",
"marked": "^10.0.0",
Expand Down
2 changes: 1 addition & 1 deletion apps/desktop/src/lib/branch/BranchCard.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -156,7 +156,7 @@
/>
</div>
{:else if branch.commits.length === 0}
<Dropzones>
<Dropzones id={branch.name}>
<div class="new-branch">
<EmptyStatePlaceholder image={laneNewSvg} width="11rem">
<svelte:fragment slot="title">This is a new branch</svelte:fragment>
Expand Down
2 changes: 1 addition & 1 deletion apps/desktop/src/lib/branch/BranchLane.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,7 @@
});
</script>

<div class="wrapper" data-tauri-drag-region>
<div class="wrapper" data-testid="branch-{branch.name}" data-tauri-drag-region>
<BranchCard {commitBoxOpen} {isLaneCollapsed} />

{#await $selectedFile then [commitId, selected]}
Expand Down
4 changes: 3 additions & 1 deletion apps/desktop/src/lib/branch/Dropzones.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,10 @@
interface Props {
children: Snippet;
id?: string;
}
const { children }: Props = $props();
const { children, id }: Props = $props();
const actions = $derived(branchDragActionsFactory.build($branch));
</script>
Expand Down Expand Up @@ -42,6 +43,7 @@
accepts={actions.acceptBranchDrop.bind(actions)}
ondrop={actions.onBranchDrop.bind(actions)}
fillHeight
id={id ? id + '-files-dz' : undefined}
>
{@render children()}

Expand Down
2 changes: 1 addition & 1 deletion apps/desktop/src/lib/dragging/dropzone.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,9 @@ export class Dropzone {
this.registerListeners();

// Mark the dropzone as active
this.activated = true;
setTimeout(() => {
this.configuration.onActivationStart();
this.activated = true;
}, 10);
}

Expand Down
3 changes: 3 additions & 0 deletions apps/desktop/src/lib/dropzone/Dropzone.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
interface Props {
disabled?: boolean;
fillHeight?: boolean;
id?: string;
accepts: (data: any) => boolean;
ondrop: (data: any) => Promise<void> | void;
overlay: Snippet<[{ hovered: boolean; activated: boolean }]>;
Expand All @@ -14,6 +15,7 @@
const {
disabled = false,
fillHeight = false,
id,
accepts,
ondrop,
overlay,
Expand Down Expand Up @@ -53,6 +55,7 @@
target: '.dropzone-target'
}}
class:fill-height={fillHeight}
data-testid={id}
class="dropzone-container"
>
{@render overlay({ hovered, activated })}
Expand Down
24 changes: 12 additions & 12 deletions apps/desktop/src/lib/file/FileListItem.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -166,18 +166,18 @@
draggableEl && addAnimationEndListener(draggableEl);
}

onDestroy(() => {
// Ensure any listeners are removed if the component is destroyed before animation ends
if (draggableEl && animationEndHandler) {
draggableEl.removeEventListener('animationend', animationEndHandler);
}
files.forEach((f) => {
const lockedElement = document.getElementById(`file-${f.id}`);
if (lockedElement && animationEndHandler) {
lockedElement.removeEventListener('animationend', animationEndHandler);
}
});
});
// onDestroy(() => {
// // Ensure any listeners are removed if the component is destroyed before animation ends
// if (draggableEl && animationEndHandler) {
// draggableEl.removeEventListener('animationend', animationEndHandler);
// }
// files.forEach((f) => {
// const lockedElement = document.getElementById(`file-${f.id}`);
// if (lockedElement && animationEndHandler) {
// lockedElement.removeEventListener('animationend', animationEndHandler);
// }
// });
// });
}}
oncontextmenu={async (e) => {
if (fileIdSelection.has(file.id, $commit?.id)) {
Expand Down
1 change: 1 addition & 0 deletions packages/ui/src/lib/file/FileListItem.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@
tabindex="-1"
{onclick}
{onkeydown}
data-testid={'file-' + filePath}
oncontextmenu={(e) => {
if (oncontextmenu) {
e.preventDefault();
Expand Down
Loading

0 comments on commit 29b2b6b

Please sign in to comment.