Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Added ui:*Template properties #1152

Merged
merged 8 commits into from Jul 13, 2019
4 changes: 2 additions & 2 deletions package.json
Expand Up @@ -7,8 +7,8 @@
"build:lib": "rimraf lib && cross-env NODE_ENV=production babel -d lib/ src/",
"build:dist": "rimraf dist && cross-env NODE_ENV=production webpack --config webpack.config.dist.js",
"build:playground": "rimraf build && cross-env NODE_ENV=production webpack --config webpack.config.prod.js && cp playground/index.prod.html build/index.html",
"cs-check": "prettier -l $npm_package_prettierOptions '{playground,src,test}/**/*.js'",
epicfaace marked this conversation as resolved.
Show resolved Hide resolved
"cs-format": "prettier --jsx-bracket-same-line --trailing-comma es5 --use-tabs false --semi --tab-width 2 '{playground,src,test}/**/*.js' --write",
"cs-check": "prettier -l $npm_package_prettierOptions \"{playground,src,test}/**/*.js\"",
"cs-format": "prettier --jsx-bracket-same-line --trailing-comma es5 --use-tabs false --semi --tab-width 2 \"{playground,src,test}/**/*.js\" --write",
"dist": "npm run build:lib && npm run build:dist",
"lint": "eslint src test playground",
"prepare": "npm run dist",
Expand Down
10 changes: 8 additions & 2 deletions src/components/fields/ArrayField.js
Expand Up @@ -411,7 +411,10 @@ class ArrayField extends Component {
};

// Check if a custom render function was passed in
const Component = ArrayFieldTemplate || DefaultNormalArrayFieldTemplate;
const Component =
uiSchema["ui:ArrayFieldTemplate"] ||
ArrayFieldTemplate ||
DefaultNormalArrayFieldTemplate;
return <Component {...arrayProps} />;
}

Expand Down Expand Up @@ -585,7 +588,10 @@ class ArrayField extends Component {
};

// Check if a custom template template was passed in
const Template = ArrayFieldTemplate || DefaultFixedArrayFieldTemplate;
const Template =
uiSchema["ui:ArrayFieldTemplate"] ||
ArrayFieldTemplate ||
DefaultFixedArrayFieldTemplate;
return <Template {...arrayProps} />;
}

Expand Down
5 changes: 4 additions & 1 deletion src/components/fields/ObjectField.js
Expand Up @@ -212,7 +212,10 @@ class ObjectField extends Component {
);
}

const Template = registry.ObjectFieldTemplate || DefaultObjectFieldTemplate;
const Template =
uiSchema["ui:ObjectFieldTemplate"] ||
registry.ObjectFieldTemplate ||
DefaultObjectFieldTemplate;

const templateProps = {
title: uiSchema["ui:title"] || title,
Expand Down
9 changes: 3 additions & 6 deletions src/components/fields/SchemaField.js
Expand Up @@ -221,12 +221,9 @@ function SchemaFieldRender(props) {
required,
registry = getDefaultRegistry(),
} = props;
const {
definitions,
fields,
formContext,
FieldTemplate = DefaultTemplate,
} = registry;
const { definitions, fields, formContext } = registry;
const FieldTemplate =
uiSchema["ui:FieldTemplate"] || registry.FieldTemplate || DefaultTemplate;
let idSchema = props.idSchema;
const schema = retrieveSchema(props.schema, definitions, formData);
idSchema = mergeObjects(
Expand Down
221 changes: 141 additions & 80 deletions test/ArrayFieldTemplate_test.js
Expand Up @@ -46,14 +46,33 @@ describe("ArrayFieldTemplate", () => {
}
}

it("should render a stateful custom component", () => {
const { node } = createFormComponent({
schema: { type: "array", items: { type: "string" } },
formData,
ArrayFieldTemplate,
describe("with template globally configured", () => {
it("should render a stateful custom component", () => {
const { node } = createFormComponent({
schema: { type: "array", items: { type: "string" } },
formData,
ArrayFieldTemplate,
});

expect(node.querySelectorAll(".field-array div")).to.have.length.of(
6
);
});
});
describe("with template configured in ui:ArrayFieldTemplate", () => {
it("should render a stateful custom component", () => {
const { node } = createFormComponent({
schema: { type: "array", items: { type: "string" } },
formData,
uiSchema: {
"ui:ArrayFieldTemplate": ArrayFieldTemplate,
},
});

expect(node.querySelectorAll(".field-array div")).to.have.length.of(
6
);
});

expect(node.querySelectorAll(".field-array div")).to.have.length.of(6);
});
});

Expand All @@ -65,52 +84,74 @@ describe("ArrayFieldTemplate", () => {
items: { type: "string" },
};

const uiSchema = {
classNames: "custom-array",
};

let node;

beforeEach(() => {
node = createFormComponent({
ArrayFieldTemplate,
formData,
schema,
uiSchema,
}).node;
});
describe("with template globally configured", () => {
const uiSchema = {
classNames: "custom-array",
};

beforeEach(() => {
node = createFormComponent({
ArrayFieldTemplate,
formData,
schema,
uiSchema,
}).node;
});

it("should render one root element for the array", () => {
expect(node.querySelectorAll(".custom-array")).to.have.length.of(1);
sharedIts();
});

it("should render one add button", () => {
expect(node.querySelectorAll(".custom-array-add")).to.have.length.of(1);
describe("with template configured in ui:ArrayFieldTemplate", () => {
const uiSchema = {
classNames: "custom-array",
"ui:ArrayFieldTemplate": ArrayFieldTemplate,
};

beforeEach(() => {
node = createFormComponent({
formData,
schema,
uiSchema,
}).node;
});
sharedIts();
});
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add a test in which a template is globally configured and a template is configured in ui:ArrayFieldTemplate so it has to override?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added

function sharedIts() {
it("should render one root element for the array", () => {
expect(node.querySelectorAll(".custom-array")).to.have.length.of(1);
});

it("should render one child for each array item", () => {
expect(node.querySelectorAll(".custom-array-item")).to.have.length.of(
formData.length
);
});
it("should render one add button", () => {
expect(node.querySelectorAll(".custom-array-add")).to.have.length.of(
1
);
});

it("should render text input for each array item", () => {
expect(
node.querySelectorAll(".custom-array-item .field input[type=text]")
).to.have.length.of(formData.length);
});
it("should render one child for each array item", () => {
expect(node.querySelectorAll(".custom-array-item")).to.have.length.of(
formData.length
);
});

it("should render move up button for all but one array items", () => {
expect(
node.querySelectorAll(".custom-array-item-move-up")
).to.have.length.of(formData.length - 1);
});
it("should render text input for each array item", () => {
expect(
node.querySelectorAll(".custom-array-item .field input[type=text]")
).to.have.length.of(formData.length);
});

it("should render move down button for all but one array items", () => {
expect(
node.querySelectorAll(".custom-array-item-move-down")
).to.have.length.of(formData.length - 1);
});
it("should render move up button for all but one array items", () => {
expect(
node.querySelectorAll(".custom-array-item-move-up")
).to.have.length.of(formData.length - 1);
});

it("should render move down button for all but one array items", () => {
expect(
node.querySelectorAll(".custom-array-item-move-down")
).to.have.length.of(formData.length - 1);
});
}
});

describe("fixed items", () => {
Expand All @@ -121,52 +162,72 @@ describe("ArrayFieldTemplate", () => {
items: [{ type: "string" }, { type: "string" }, { type: "string" }],
};

const uiSchema = {
classNames: "custom-array",
};

let node;

beforeEach(() => {
node = createFormComponent({
ArrayFieldTemplate,
formData,
schema,
uiSchema,
}).node;
describe("with template globally configured", () => {
const uiSchema = {
classNames: "custom-array",
};
beforeEach(() => {
node = createFormComponent({
formData,
schema,
uiSchema,
ArrayFieldTemplate,
}).node;
});
sharedIts();
});

it("should render one root element for the array", () => {
expect(node.querySelectorAll(".custom-array")).to.have.length.of(1);
describe("with template configured in ui:ArrayFieldTemplate", () => {
const uiSchema = {
classNames: "custom-array",
"ui:ArrayFieldTemplate": ArrayFieldTemplate,
};
beforeEach(() => {
node = createFormComponent({
formData,
schema,
uiSchema,
}).node;
});
sharedIts();
});
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add a test in which a template is globally configured and a template is configured in ui:ArrayFieldTemplate so it has to override?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added

function sharedIts() {
it("should render one root element for the array", () => {
expect(node.querySelectorAll(".custom-array")).to.have.length.of(1);
});

it("should not render an add button", () => {
expect(node.querySelectorAll(".custom-array-add")).to.have.length.of(0);
});
it("should not render an add button", () => {
expect(node.querySelectorAll(".custom-array-add")).to.have.length.of(
0
);
});

it("should render one child for each array item", () => {
expect(node.querySelectorAll(".custom-array-item")).to.have.length.of(
formData.length
);
});
it("should render one child for each array item", () => {
expect(node.querySelectorAll(".custom-array-item")).to.have.length.of(
formData.length
);
});

it("should render text input for each array item", () => {
expect(
node.querySelectorAll(".custom-array-item .field input[type=text]")
).to.have.length.of(formData.length);
});
it("should render text input for each array item", () => {
expect(
node.querySelectorAll(".custom-array-item .field input[type=text]")
).to.have.length.of(formData.length);
});

it("should not render any move up buttons", () => {
expect(
node.querySelectorAll(".custom-array-item-move-up")
).to.have.length.of(0);
});
it("should not render any move up buttons", () => {
expect(
node.querySelectorAll(".custom-array-item-move-up")
).to.have.length.of(0);
});

it("should not render any move down buttons", () => {
expect(
node.querySelectorAll(".custom-array-item-move-down")
).to.have.length.of(0);
});
it("should not render any move down buttons", () => {
expect(
node.querySelectorAll(".custom-array-item-move-down")
).to.have.length.of(0);
});
}
});
});
});
43 changes: 31 additions & 12 deletions test/FieldTemplate_test.js
Expand Up @@ -19,22 +19,41 @@ describe("FieldTemplate", () => {
return <div className={props.disabled ? "disabled" : "foo"} />;
}

it("should render with disabled when ui:disabled is truthy", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": true },
FieldTemplate,
describe("with template globally configured", () => {
it("should render with disabled when ui:disabled is truthy", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": true },
FieldTemplate,
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(1);
});

it("should render with disabled when ui:disabled is falsey", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": false },
FieldTemplate,
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(0);
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(1);
});
describe("with template configured in ui:ObjectFieldTemplate", () => {
loganvolkers marked this conversation as resolved.
Show resolved Hide resolved
it("should render with disabled when ui:disabled is truthy", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": true, "ui:FieldTemplate": FieldTemplate },
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(1);
});

it("should render with disabled when ui:disabled is falsey", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": false },
FieldTemplate,
it("should render with disabled when ui:disabled is falsey", () => {
const { node } = createFormComponent({
schema: { type: "string" },
uiSchema: { "ui:disabled": false, "ui:FieldTemplate": FieldTemplate },
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(0);
});
expect(node.querySelectorAll(".disabled")).to.have.length.of(0);
});
epicfaace marked this conversation as resolved.
Show resolved Hide resolved
});
});