Skip to content

Commit

Permalink
Merge branch 'master' of github.com:mattermost-community/mattermost-p…
Browse files Browse the repository at this point in the history
…lugin-todo into fix_issue_216
  • Loading branch information
raghavaggarwal2308 committed Jul 18, 2024
2 parents dcbb4b2 + 5e3aa74 commit e097e49
Show file tree
Hide file tree
Showing 10 changed files with 199 additions and 150 deletions.
7 changes: 7 additions & 0 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
version: 2
updates:
# Enable version updates for GOLang dependencies
- package-ecosystem: "gomod"
directory: "/"
schedule:
interval: "monthly"
10 changes: 1 addition & 9 deletions .github/workflows/cd.yml
Original file line number Diff line number Diff line change
@@ -1,18 +1,10 @@
name: cd
on:
workflow_run:
workflows: ["ci"]
branches-ignore: ["*"]
types:
- completed
push:
tags:
- "v*"

permissions:
contents: read

jobs:
plugin-cd:
uses: mattermost/actions-workflows/.github/workflows/plugin-cd.yml@main
uses: mattermost/actions-workflows/.github/workflows/community-plugin-cd.yml@d9defa3e455bdbf889573e112ad8d05b91d66b4c
secrets: inherit
12 changes: 3 additions & 9 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -1,18 +1,12 @@
name: ci
on:
schedule:
- cron: "0 0 * * *"
pull_request:
push:
branches:
- master
tags:
- "v*"
pull_request:

permissions:
contents: read
- main

jobs:
plugin-ci:
uses: mattermost/actions-workflows/.github/workflows/plugin-ci.yml@main
uses: mattermost/actions-workflows/.github/workflows/community-plugin-ci.yml@139a051e8651e6246e3764fe342297b73120e590
secrets: inherit
3 changes: 1 addition & 2 deletions e2e/playwright/tests/test.list.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.

import {test} from '@playwright/test';
import core from './todo_plugin.spec';

import '../support/init_test';

test.describe(core.connected);
core.connected();
6 changes: 2 additions & 4 deletions e2e/playwright/tests/todo_plugin.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,16 +13,15 @@ import {fillMessage, getTodoBotDMPageURL} from 'support/utils';
export default {
connected: () => {
test.describe('available commands', () => {
test('with just the main command', async ({pages, page, pw}) => {
test('with just the main command', async ({page, pw}) => {

const {adminClient, adminUser} = await pw.getAdminClient();
if (adminUser === null) {
throw new Error('can not get adminUser');
}
const dmURL = await getTodoBotDMPageURL(adminClient, '', adminUser.id);
await page.goto(dmURL, {waitUntil: 'load'});

const c = new pages.ChannelsPage(page);
const slash = new SlashCommandSuggestions(page.locator('#suggestionList'));

// # Run incomplete command to trigger help
Expand All @@ -39,4 +38,3 @@ export default {
});
},
};

6 changes: 4 additions & 2 deletions server/list.go
Original file line number Diff line number Diff line change
Expand Up @@ -245,8 +245,10 @@ func (l *listManager) ChangeAssignment(issueID string, userID string, sendTo str
return issue.Message, ir.ForeignUserID, nil
}

if err := l.store.RemoveReference(userID, issueID, list); err != nil {
return "", "", err
if userID != sendTo {
if err := l.store.RemoveReference(userID, issueID, list); err != nil {
return "", "", err
}
}

receiverIssue := newIssue(issue.Message, issue.Description, issue.PostID)
Expand Down
142 changes: 142 additions & 0 deletions webapp/src/components/assignee_modal/assignee_form.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
import React, {useState, useCallback} from 'react';
import PropTypes from 'prop-types';

import AutocompleteSelector from '../user_selector/autocomplete_selector';
import Button from '../../widget/buttons/button';
import IconButton from '../../widget/iconButton/iconButton';

import CompassIcon from '../icons/compassIcons';

import {useEscapeKey} from '../../hooks/useEscapeKey';

const AssigneeForm = (
{
close,
autocompleteUsers,
theme,
getAssignee,
removeAssignee,
removeEditingTodo,
changeAssignee,
editingTodo,
},
) => {
const [assignee, setAssignee] = useState();
useEscapeKey(close);
const submit = useCallback(() => {
if (editingTodo && assignee) {
changeAssignee(editingTodo, assignee.username);
removeEditingTodo();
} else if (assignee) {
getAssignee(assignee);
} else {
removeAssignee();
}
close();
}, [close, changeAssignee, removeAssignee, getAssignee, assignee, removeEditingTodo, editingTodo]);

const closeModal = () => {
removeEditingTodo();
close();
};

const changeAssigneeDropdown = (selected) => {
setAssignee(selected);
};

const style = getStyle(theme);

return (
<div
style={style.backdrop}
>
<div style={style.modal}>
<h1 style={style.heading}>{'Assign todo to…'}</h1>
<IconButton
size='medium'
style={style.closeIcon}
onClick={closeModal}
icon={<CompassIcon icon='close'/>}
/>
<AutocompleteSelector
autoFocus={true}
id='send_to_user'
loadOptions={autocompleteUsers}
onSelected={changeAssigneeDropdown}
placeholder={''}
theme={theme}
/>
<div
className='todoplugin-button-container'
style={style.buttons}
>
<Button
emphasis='tertiary'
size='medium'
onClick={closeModal}
>
{'Cancel'}
</Button>
<Button
emphasis='primary'
size='medium'
onClick={submit}
disabled={!assignee}
>
{'Assign'}
</Button>
</div>
</div>
</div>
);
};

AssigneeForm.propTypes = {
close: PropTypes.func.isRequired,
theme: PropTypes.object.isRequired,
autocompleteUsers: PropTypes.func.isRequired,
getAssignee: PropTypes.func.isRequired,
editingTodo: PropTypes.string.isRequired,
removeAssignee: PropTypes.func.isRequired,
removeEditingTodo: PropTypes.func.isRequired,
changeAssignee: PropTypes.func.isRequired,
};

const getStyle = (theme) => ({
backdrop: {
position: 'absolute',
display: 'flex',
top: 0,
left: 0,
right: 0,
bottom: 0,
backgroundColor: 'rgba(0, 0, 0, 0.50)',
zIndex: 2000,
alignItems: 'center',
justifyContent: 'center',
},
modal: {
position: 'relative',
width: 600,
padding: 24,
borderRadius: 8,
maxWidth: '100%',
color: theme.centerChannelColor,
backgroundColor: theme.centerChannelBg,
},
buttons: {
marginTop: 24,
},
heading: {
fontSize: 20,
fontWeight: 600,
margin: '0 0 24px 0',
},
closeIcon: {
position: 'absolute',
top: 8,
right: 8,
},
});

export default AssigneeForm;
135 changes: 12 additions & 123 deletions webapp/src/components/assignee_modal/assignee_modal.jsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,7 @@
import React, {useState, useEffect, useCallback} from 'react';
import React from 'react';
import PropTypes from 'prop-types';

import AutocompleteSelector from '../user_selector/autocomplete_selector.tsx';
import Button from '../../widget/buttons/button';
import IconButton from '../../widget/iconButton/iconButton';

import CompassIcon from '../icons/compassIcons';
import AssigneeForm from './assignee_form';

const AssigneeModal = (
{
Expand All @@ -20,91 +16,21 @@ const AssigneeModal = (
editingTodo,
},
) => {
const [assignee, setAssignee] = useState();

useEffect(() => {
function handleKeypress(e) {
if (e.key === 'Escape' && visible) {
close();
}
}

document.addEventListener('keyup', handleKeypress);

return () => {
document.removeEventListener('keyup', handleKeypress);
};
}, [visible]);

const submit = useCallback(() => {
if (editingTodo && assignee) {
changeAssignee(editingTodo, assignee.username);
removeEditingTodo();
} else if (assignee) {
getAssignee(assignee);
} else {
removeAssignee();
}
close();
}, [close, changeAssignee, removeAssignee, getAssignee, assignee, removeEditingTodo, editingTodo]);

if (!visible) {
return null;
}

const closeModal = () => {
removeEditingTodo();
close();
};

const changeAssigneeDropdown = (selected) => {
setAssignee(selected);
};

const style = getStyle(theme);

return (
<div
style={style.backdrop}
>
<div style={style.modal}>
<h1 style={style.heading}>{'Assign todo to…'}</h1>
<IconButton
size='medium'
style={style.closeIcon}
onClick={closeModal}
icon={<CompassIcon icon='close'/>}
/>
<AutocompleteSelector
autoFocus={true}
id='send_to_user'
loadOptions={autocompleteUsers}
onSelected={changeAssigneeDropdown}
placeholder={''}
theme={theme}
/>
<div
className='todoplugin-button-container'
style={style.buttons}
>
<Button
emphasis='tertiary'
size='medium'
onClick={closeModal}
>
{'Cancel'}
</Button>
<Button
emphasis='primary'
size='medium'
onClick={submit}
disabled={!assignee}
>
{'Assign'}
</Button>
</div>
</div>
</div>
<AssigneeForm
autocompleteUsers={autocompleteUsers}
changeAssignee={changeAssignee}
close={close}
editingTodo={editingTodo}
getAssignee={getAssignee}
removeAssignee={removeAssignee}
removeEditingTodo={removeEditingTodo}
theme={theme}
/>
);
};

Expand All @@ -120,41 +46,4 @@ AssigneeModal.propTypes = {
changeAssignee: PropTypes.func.isRequired,
};

const getStyle = (theme) => ({
backdrop: {
position: 'absolute',
display: 'flex',
top: 0,
left: 0,
right: 0,
bottom: 0,
backgroundColor: 'rgba(0, 0, 0, 0.50)',
zIndex: 2000,
alignItems: 'center',
justifyContent: 'center',
},
modal: {
position: 'relative',
width: 600,
padding: 24,
borderRadius: 8,
maxWidth: '100%',
color: theme.centerChannelColor,
backgroundColor: theme.centerChannelBg,
},
buttons: {
marginTop: 24,
},
heading: {
fontSize: 20,
fontWeight: 600,
margin: '0 0 24px 0',
},
closeIcon: {
position: 'absolute',
top: 8,
right: 8,
},
});

export default AssigneeModal;
Loading

0 comments on commit e097e49

Please sign in to comment.