mirror of
https://github.com/gristlabs/grist-core.git
synced 2026-03-02 04:09:24 +00:00
(core) Form kanban tasks
Summary: - Open all links in a new tab - Excluding not filled columns (to fix trigger formulas) - Fixed Ref/RefList submission - Removing redundant type definitions for Box - Adding header menu item - Default empty values in select control Test Plan: Updated Reviewers: georgegevoian Reviewed By: georgegevoian Differential Revision: https://phab.getgrist.com/D4166
This commit is contained in:
@@ -60,6 +60,7 @@ describe('FormView', function() {
|
||||
async function createFormWith(type: string, more = false) {
|
||||
await gu.addNewSection('Form', 'Table1');
|
||||
|
||||
// Make sure column D is not there.
|
||||
assert.isUndefined(await api.getTable(docId, 'Table1').then(t => t.D));
|
||||
|
||||
// Add a text question
|
||||
@@ -117,10 +118,62 @@ describe('FormView', function() {
|
||||
assert.deepEqual(await api.getTable(docId, 'Table1').then(t => t.D), [value]);
|
||||
}
|
||||
|
||||
async function expect(values: any[]) {
|
||||
async function expectInD(values: any[]) {
|
||||
assert.deepEqual(await api.getTable(docId, 'Table1').then(t => t.D), values);
|
||||
}
|
||||
|
||||
it('updates creator panel when navigated away', async function() {
|
||||
// Add 2 new pages.
|
||||
await gu.addNewPage('Form', 'New Table', {tableName: 'TabA'});
|
||||
await gu.renamePage('TabA');
|
||||
await gu.addNewPage('Form', 'New Table', {tableName: 'TabB'});
|
||||
|
||||
// Open the creator panel on field tab
|
||||
await gu.openColumnPanel();
|
||||
|
||||
// Select A column
|
||||
await question('A').click();
|
||||
|
||||
// Make sure it is selected.
|
||||
assert.equal(await selectedLabel(), 'A');
|
||||
|
||||
// And creator panel reflects it.
|
||||
assert.equal(await driver.find('.test-field-label').value(), "A");
|
||||
|
||||
// Now switch to page TabA.
|
||||
await gu.openPage('TabA');
|
||||
|
||||
// And select B column.
|
||||
await question('B').click();
|
||||
assert.equal(await selectedLabel(), 'B');
|
||||
|
||||
// Make sure creator panel reflects it (it didn't).
|
||||
assert.equal(await driver.find('.test-field-label').value(), "B");
|
||||
|
||||
await gu.undo(2); // There was a bug with second undo.
|
||||
await gu.undo();
|
||||
});
|
||||
|
||||
it('triggers trigger formulas', async function() {
|
||||
const formUrl = await createFormWith('Text');
|
||||
// Add a trigger formula for this column.
|
||||
await gu.showRawData();
|
||||
await gu.getCell('D', 1).click();
|
||||
await gu.openColumnPanel();
|
||||
await driver.find(".test-field-set-trigger").click();
|
||||
await gu.waitAppFocus(false);
|
||||
await gu.sendKeys('"Hello from trigger"', Key.ENTER);
|
||||
await gu.waitForServer();
|
||||
await gu.closeRawTable();
|
||||
await gu.onNewTab(async () => {
|
||||
await driver.get(formUrl);
|
||||
await driver.find('input[type="submit"]').click();
|
||||
await waitForConfirm();
|
||||
});
|
||||
await expectSingle('Hello from trigger');
|
||||
await removeForm();
|
||||
});
|
||||
|
||||
it('can submit a form with Text field', async function() {
|
||||
const formUrl = await createFormWith('Text');
|
||||
// We are in a new window.
|
||||
@@ -189,7 +242,7 @@ describe('FormView', function() {
|
||||
await gu.onNewTab(async () => {
|
||||
await driver.get(formUrl);
|
||||
// Make sure options are there.
|
||||
assert.deepEqual(await driver.findAll('select[name="D"] option', e => e.getText()), ['Foo', 'Bar', 'Baz']);
|
||||
assert.deepEqual(await driver.findAll('select[name="D"] option', e => e.getText()), ['', 'Foo', 'Bar', 'Baz']);
|
||||
await driver.findWait('select[name="D"]', 1000).click();
|
||||
await driver.find("option[value='Bar']").click();
|
||||
await driver.find('input[type="submit"]').click();
|
||||
@@ -229,7 +282,7 @@ describe('FormView', function() {
|
||||
await driver.find('input[type="submit"]').click();
|
||||
await waitForConfirm();
|
||||
});
|
||||
await expect([true, false]);
|
||||
await expectInD([true, false]);
|
||||
|
||||
// Remove the additional record added just now.
|
||||
await gu.sendActions([
|
||||
@@ -262,6 +315,78 @@ describe('FormView', function() {
|
||||
await removeForm();
|
||||
});
|
||||
|
||||
it('can submit a form with Ref field', async function() {
|
||||
const formUrl = await createFormWith('Reference', true);
|
||||
// Add some options.
|
||||
await gu.openColumnPanel();
|
||||
await gu.setRefShowColumn('A');
|
||||
// Add 3 records to this table (it is now empty).
|
||||
await gu.sendActions([
|
||||
['AddRecord', 'Table1', null, {A: 'Foo'}], // id 1
|
||||
['AddRecord', 'Table1', null, {A: 'Bar'}], // id 2
|
||||
['AddRecord', 'Table1', null, {A: 'Baz'}], // id 3
|
||||
]);
|
||||
await gu.toggleSidePanel('right', 'close');
|
||||
// We are in a new window.
|
||||
await gu.onNewTab(async () => {
|
||||
await driver.get(formUrl);
|
||||
assert.deepEqual(
|
||||
await driver.findAll('select[name="D"] option', e => e.getText()),
|
||||
['', ...['Bar', 'Baz', 'Foo']]
|
||||
);
|
||||
assert.deepEqual(
|
||||
await driver.findAll('select[name="D"] option', e => e.value()),
|
||||
['', ...['2', '3', '1']]
|
||||
);
|
||||
await driver.findWait('select[name="D"]', 1000).click();
|
||||
await driver.find('option[value="2"]').click();
|
||||
await driver.find('input[type="submit"]').click();
|
||||
await waitForConfirm();
|
||||
});
|
||||
await expectInD([0, 0, 0, 2]);
|
||||
|
||||
// Remove 3 records.
|
||||
await gu.sendActions([
|
||||
['BulkRemoveRecord', 'Table1', [1, 2, 3, 4]],
|
||||
]);
|
||||
|
||||
await removeForm();
|
||||
});
|
||||
|
||||
it('can submit a form with RefList field', async function() {
|
||||
const formUrl = await createFormWith('Reference List', true);
|
||||
// Add some options.
|
||||
await gu.openColumnPanel();
|
||||
|
||||
await gu.setRefShowColumn('A');
|
||||
// Add 3 records to this table (it is now empty).
|
||||
await gu.sendActions([
|
||||
['AddRecord', 'Table1', null, {A: 'Foo'}], // id 1
|
||||
['AddRecord', 'Table1', null, {A: 'Bar'}], // id 2
|
||||
['AddRecord', 'Table1', null, {A: 'Baz'}], // id 3
|
||||
]);
|
||||
await gu.toggleSidePanel('right', 'close');
|
||||
// We are in a new window.
|
||||
await gu.onNewTab(async () => {
|
||||
await driver.get(formUrl);
|
||||
await driver.findWait('input[name="D[]"][value="1"]', 1000).click();
|
||||
await driver.findWait('input[name="D[]"][value="2"]', 1000).click();
|
||||
assert.equal(await driver.find('.grist-checkbox:has(input[name="D[]"][value="1"])').getText(), 'Foo');
|
||||
assert.equal(await driver.find('.grist-checkbox:has(input[name="D[]"][value="2"])').getText(), 'Bar');
|
||||
assert.equal(await driver.find('.grist-checkbox:has(input[name="D[]"][value="3"])').getText(), 'Baz');
|
||||
await driver.find('input[type="submit"]').click();
|
||||
await waitForConfirm();
|
||||
});
|
||||
await expectInD([null, null, null, ['L', 2, 1]]);
|
||||
|
||||
// Remove 3 records.
|
||||
await gu.sendActions([
|
||||
['BulkRemoveRecord', 'Table1', [1, 2, 3, 4]],
|
||||
]);
|
||||
|
||||
await removeForm();
|
||||
});
|
||||
|
||||
it('can unpublish forms', async function() {
|
||||
const formUrl = await createFormWith('Text');
|
||||
await driver.find('.test-forms-unpublish').click();
|
||||
|
||||
@@ -508,7 +508,7 @@ describe('RawData', function () {
|
||||
await gu.sendKeys("abc");
|
||||
await gu.checkTextEditor("abc");
|
||||
await gu.sendKeys(Key.ESCAPE);
|
||||
await showRawData();
|
||||
await gu.showRawData();
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'City');
|
||||
assert.deepEqual(await gu.getCursorPosition(), {rowNum: 20, col: 0}); // raw popup is not sorted
|
||||
await gu.sendKeys("abc");
|
||||
@@ -530,7 +530,7 @@ describe('RawData', function () {
|
||||
await gu.sendKeys(Key.ESCAPE);
|
||||
|
||||
// Now open popup again, but close it by clicking on the close button.
|
||||
await showRawData();
|
||||
await gu.showRawData();
|
||||
await gu.closeRawTable();
|
||||
await assertNoPopup();
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'CITY');
|
||||
@@ -540,7 +540,7 @@ describe('RawData', function () {
|
||||
await gu.sendKeys(Key.ESCAPE);
|
||||
|
||||
// Now do the same, but close by clicking on a diffrent page
|
||||
await showRawData();
|
||||
await gu.showRawData();
|
||||
await gu.getPageItem('Country').click();
|
||||
await assertNoPopup();
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'COUNTRY');
|
||||
@@ -552,7 +552,7 @@ describe('RawData', function () {
|
||||
// Now make sure that raw data is available for card view.
|
||||
await gu.selectSectionByTitle("COUNTRY Card List");
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'COUNTRY Card List');
|
||||
await showRawData();
|
||||
await gu.showRawData();
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'Country');
|
||||
assert.deepEqual(await gu.getCursorPosition(), {rowNum: 1, col: 1});
|
||||
await gu.sendKeys("abc");
|
||||
@@ -623,7 +623,7 @@ describe('RawData', function () {
|
||||
// Now open plain raw data for City table.
|
||||
await gu.selectSectionByTitle("CITY");
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'CITY'); // CITY is viewSection title
|
||||
await showRawData();
|
||||
await gu.showRawData();
|
||||
assert.equal(await gu.getActiveSectionTitle(), 'City'); // City is now a table title
|
||||
// Now remove the table.
|
||||
await api.applyUserActions(doc, [[
|
||||
@@ -787,12 +787,6 @@ function replaceAnchor(link: string, values: {
|
||||
return link.replace(anchorRegex, `#a${values.a || a}.s${values.s || s}.r${values.r || r}.c${values.c || c}`);
|
||||
}
|
||||
|
||||
async function showRawData() {
|
||||
await gu.openSectionMenu('viewLayout');
|
||||
await driver.find('.test-show-raw-data').click();
|
||||
await waitForPopup();
|
||||
}
|
||||
|
||||
async function openRawData() {
|
||||
await driver.find('.test-tools-raw').click();
|
||||
await waitForRawData();
|
||||
|
||||
@@ -1188,7 +1188,12 @@ export async function changeWidget(type: WidgetType) {
|
||||
/**
|
||||
* Rename the given page to a new name. The oldName can be a full string name or a RegExp.
|
||||
*/
|
||||
export async function renamePage(oldName: string|RegExp, newName: string) {
|
||||
export async function renamePage(oldName: string|RegExp, newName?: string) {
|
||||
if (!newName && typeof oldName === 'string') {
|
||||
newName = oldName;
|
||||
oldName = await getCurrentPageName();
|
||||
}
|
||||
if (newName === undefined) { throw new Error('newName must be specified'); }
|
||||
await openPageMenu(oldName);
|
||||
await driver.find('.test-docpage-rename').click();
|
||||
await driver.find('.test-docpage-editor').sendKeys(newName, Key.ENTER);
|
||||
@@ -1570,6 +1575,15 @@ export async function openSectionMenu(which: 'sortAndFilter'|'viewLayout', secti
|
||||
return await driver.findWait('.grist-floating-menu', 100);
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens Raw data view for current section.
|
||||
*/
|
||||
export async function showRawData(section?: string|WebElement) {
|
||||
await openSectionMenu('viewLayout', section);
|
||||
await driver.find('.test-show-raw-data').click();
|
||||
assert.isTrue(await driver.findWait('.test-raw-data-overlay', 100).isDisplayed());
|
||||
}
|
||||
|
||||
// Mapping from column menu option name to dom element selector to wait for, or null if no need to wait.
|
||||
const ColumnMenuOption: { [id: string]: string; } = {
|
||||
Filter: '.test-filter-menu-wrapper'
|
||||
|
||||
Reference in New Issue
Block a user