+ );
+};
+
+export default FormRepeater;
diff --git a/src/components/forms/inventory-item-form.js b/src/components/forms/inventory-item-form.js
new file mode 100644
index 000000000..1bb8a2340
--- /dev/null
+++ b/src/components/forms/inventory-item-form.js
@@ -0,0 +1,175 @@
+/**
+ * Copyright 2024 OpenStack Foundation
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * */
+
+import React, { useState, useEffect } from "react";
+import T from "i18n-react/dist/i18n-react";
+import "awesome-bootstrap-checkbox/awesome-bootstrap-checkbox.css";
+import {
+ Dropdown,
+ Input,
+ TextEditor
+} from "openstack-uicore-foundation/lib/components";
+import FormRepeater from "../form-repeater";
+import {
+ scrollToError,
+ shallowEqual,
+ hasErrors
+} from "../../utils/methods";
+
+const InventoryItemForm = ({
+ entity: initialEntity,
+ errors: initialErrors,
+ onSubmit
+}) => {
+ const [entity, setEntity] = useState({ ...initialEntity });
+ const [errors, setErrors] = useState(initialErrors);
+
+ useEffect(() => {
+ scrollToError(initialErrors);
+ if (!shallowEqual(initialEntity, entity)) {
+ setEntity({ ...initialEntity });
+ setErrors({});
+ }
+
+ if (!shallowEqual(initialErrors, errors)) {
+ setErrors({ ...initialErrors });
+ }
+ }, [initialEntity, initialErrors]);
+
+ const handleChange = (ev) => {
+ const { id, value, checked, type } = ev.target;
+ setEntity((prevEntity) => ({
+ ...prevEntity,
+ [id]: type === "checkbox" ? checked : value
+ }));
+ setErrors((prevErrors) => ({ ...prevErrors, [id]: "" }));
+ };
+
+ const handleSubmit = (ev) => {
+ ev.preventDefault();
+ onSubmit(entity);
+ };
+
+ // const renderLineContent = (line, updateValue) => (
+ const renderLineContent = () => (
+
+
+
+
+
+
+
+
+
+
+
+ {}}
+ // options={(filters_ddl) => {}}
+ />
+
+
+
+
+
+ );
+
+ return (
+
+ );
+};
+
+export default InventoryItemForm;
diff --git a/src/components/menu/index.js b/src/components/menu/index.js
index 329a54fd4..4be9b683a 100644
--- a/src/components/menu/index.js
+++ b/src/components/menu/index.js
@@ -49,6 +49,17 @@ const getGlobalItems = () => [
linkUrl: "companies",
accessRoute: "companies"
},
+ {
+ name: "sponsors_inventory",
+ iconClass: "fa-users",
+ accessRoute: "sponsors-inventory",
+ childs: [
+ {
+ name: "inventory",
+ linkUrl: "sponsors-inventory/inventory"
+ }
+ ]
+ },
{
name: "sponsorship_types",
iconClass: "fa fa-handshake-o",
diff --git a/src/i18n/en.json b/src/i18n/en.json
index ab67e2579..e38396d53 100644
--- a/src/i18n/en.json
+++ b/src/i18n/en.json
@@ -157,7 +157,10 @@
"schedule_settings": "Schedule",
"registration_stats": "Registration Stats",
"audit_log": "Audit Log",
- "submission_invitations": "Submission Invitations"
+ "submission_invitations": "Submission Invitations",
+ "sponsors_inventory": "Sponsors",
+ "form_templates": "Form Templates",
+ "inventory": "Inventory"
},
"schedule": {
"schedule": "Schedule",
@@ -3154,5 +3157,23 @@
},
"url_input": {
"url_error": "URL must start with http:// or https://"
+ },
+ "sponsors_inventory": {
+ "inventory": "Inventory"
+ },
+ "inventory_item_list": {
+ "inventory_items": "Inventory Items",
+ "delete_inventory_item_warning": "Are you sure you want to delete inventory item ",
+ "add_inventory_item": "Create new Item",
+ "placeholders": {
+ "search_inventory_items": "Search"
+ }
+ },
+ "edit_inventory_item": {
+ "inventory_item": "Item",
+ "inventory_item_created": "Inventory Item created successfully.",
+ "code": "Code",
+ "name": "Name",
+ "description": "Description"
}
}
diff --git a/src/layouts/inventory-item-layout.js b/src/layouts/inventory-item-layout.js
new file mode 100644
index 000000000..40e2fc2c5
--- /dev/null
+++ b/src/layouts/inventory-item-layout.js
@@ -0,0 +1,55 @@
+/**
+ * Copyright 2024 OpenStack Foundation
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * */
+
+import React from "react";
+import { Switch, Route, withRouter } from "react-router-dom";
+import T from "i18n-react/dist/i18n-react";
+import { Breadcrumb } from "react-breadcrumbs";
+import Restrict from "../routes/restrict";
+import InventoryListPage from "../pages/sponsors_inventory/inventory-list-page";
+import EditInventoryItemPage from "../pages/sponsors_inventory/edit-inventory-item-page";
+import NoMatchPage from "../pages/no-match-page";
+
+const InventoryItemLayout = ({ match }) => (
+
+
+
+
+
+
+
+
+
+ );
+
+export default Restrict(withRouter(InventoryItemLayout), "inventory-item");
diff --git a/src/layouts/primary-layout.js b/src/layouts/primary-layout.js
index 06a369534..1d4a8ff49 100644
--- a/src/layouts/primary-layout.js
+++ b/src/layouts/primary-layout.js
@@ -21,6 +21,7 @@ import SummitLayout from "./summit-layout";
import SummitDirectoryPage from "../pages/summits/summit-directory-page";
import SpeakerLayout from "./speaker-layout";
import CompanyLayout from "./company-layout";
+import SponsorInventoryLayout from "./sponsor-inventory-layout";
import EmailLayout from "./email-layout";
import AdminAccessLayout from "./admin-access-layout";
import MediaFileTypeLayout from "./media-file-type-layout";
@@ -61,6 +62,10 @@ const PrimaryLayout = ({ match, currentSummit, location, member }) => {
/>
+ (
+
+
+
+
+
+
+
+ );
+
+export default Restrict(
+ withRouter(SponsorInventoryLayout),
+ "sponsors-inventory"
+);
diff --git a/src/pages/sponsors_inventory/edit-inventory-item-page.js b/src/pages/sponsors_inventory/edit-inventory-item-page.js
new file mode 100644
index 000000000..cc46c5c9a
--- /dev/null
+++ b/src/pages/sponsors_inventory/edit-inventory-item-page.js
@@ -0,0 +1,73 @@
+/**
+ * Copyright 2024 OpenStack Foundation
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ * */
+
+import React, { useEffect } from "react";
+import { connect } from "react-redux";
+import { Breadcrumb } from "react-breadcrumbs";
+import T from "i18n-react/dist/i18n-react";
+import InventoryItemForm from "../../components/forms/inventory-item-form";
+import {
+ getInventoryItem,
+ resetInventoryItemForm,
+ saveInventoryItem
+} from "../../actions/inventory-item-actions";
+
+const EditInventoryItemPage = (props) => {
+ const {
+ match,
+ entity,
+ errors,
+ getInventoryItem,
+ resetInventoryItemForm,
+ saveInventoryItem
+ } = props;
+ const inventoryItemId = match.params.inventory_item_id;
+
+ useEffect(() => {
+ if (!inventoryItemId) {
+ resetInventoryItemForm();
+ } else {
+ getInventoryItem(inventoryItemId);
+ }
+ }, [inventoryItemId, getInventoryItem, resetInventoryItemForm]);
+
+ const title = entity.id
+ ? T.translate("general.edit")
+ : T.translate("general.add");
+ const breadcrumb = entity.id ? entity.name : T.translate("general.new");
+
+ return (
+