mirror of
https://github.com/casdoor/casdoor.git
synced 2025-07-17 04:03:23 +08:00

* feat: integrate external model editor and handle message events for model updates * feat: add CasbinEditor and IframeEditor components for model editing * feat: add tabbed editor interface for CasbinEditor * fix: Synchronize content between basic and advanced editors * refactor: simplify CasbinEditor and ModelEditPage components * refactor: Refactor CasbinEditor for improved iframe initialization and model synchronization * refactor: update default state of CasbinEditor active tab to "advanced * chore: add Apache License header to CasbinEditor.js and IframeEditor.js files * refactor: update CasbinEditor class names for consistency
98 lines
3.3 KiB
JavaScript
98 lines
3.3 KiB
JavaScript
// Copyright 2024 The Casdoor Authors. All Rights Reserved.
|
|
//
|
|
// 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, {useCallback, useEffect, useRef, useState} from "react";
|
|
import {Controlled as CodeMirror} from "react-codemirror2";
|
|
import "codemirror/lib/codemirror.css";
|
|
import "codemirror/mode/properties/properties";
|
|
import * as Setting from "./Setting";
|
|
import IframeEditor from "./IframeEditor";
|
|
import {Tabs} from "antd";
|
|
|
|
const {TabPane} = Tabs;
|
|
|
|
const CasbinEditor = ({model, onModelTextChange}) => {
|
|
const [activeKey, setActiveKey] = useState("advanced");
|
|
const iframeRef = useRef(null);
|
|
const [localModelText, setLocalModelText] = useState(model.modelText);
|
|
|
|
const handleModelTextChange = useCallback((newModelText) => {
|
|
if (!Setting.builtInObject(model)) {
|
|
setLocalModelText(newModelText);
|
|
onModelTextChange(newModelText);
|
|
}
|
|
}, [model, onModelTextChange]);
|
|
|
|
const syncModelText = useCallback(() => {
|
|
return new Promise((resolve) => {
|
|
if (activeKey === "advanced" && iframeRef.current) {
|
|
const handleSyncMessage = (event) => {
|
|
if (event.data.type === "modelUpdate") {
|
|
window.removeEventListener("message", handleSyncMessage);
|
|
handleModelTextChange(event.data.modelText);
|
|
resolve();
|
|
}
|
|
};
|
|
window.addEventListener("message", handleSyncMessage);
|
|
iframeRef.current.getModelText();
|
|
} else {
|
|
resolve();
|
|
}
|
|
});
|
|
}, [activeKey, handleModelTextChange]);
|
|
|
|
const handleTabChange = (key) => {
|
|
syncModelText().then(() => {
|
|
setActiveKey(key);
|
|
if (key === "advanced" && iframeRef.current) {
|
|
iframeRef.current.updateModelText(localModelText);
|
|
}
|
|
});
|
|
};
|
|
|
|
useEffect(() => {
|
|
setLocalModelText(model.modelText);
|
|
}, [model.modelText]);
|
|
|
|
return (
|
|
<div style={{height: "100%", width: "100%", display: "flex", flexDirection: "column"}}>
|
|
<Tabs activeKey={activeKey} onChange={handleTabChange} style={{flex: "0 0 auto", marginTop: "-10px"}}>
|
|
<TabPane tab="Basic Editor" key="basic" />
|
|
<TabPane tab="Advanced Editor" key="advanced" />
|
|
</Tabs>
|
|
<div style={{flex: "1 1 auto", overflow: "hidden"}}>
|
|
{activeKey === "advanced" ? (
|
|
<IframeEditor
|
|
ref={iframeRef}
|
|
initialModelText={localModelText}
|
|
onModelTextChange={handleModelTextChange}
|
|
style={{width: "100%", height: "100%"}}
|
|
/>
|
|
) : (
|
|
<CodeMirror
|
|
value={localModelText}
|
|
className="full-height-editor no-horizontal-scroll-editor"
|
|
options={{mode: "properties", theme: "default"}}
|
|
onBeforeChange={(editor, data, value) => {
|
|
handleModelTextChange(value);
|
|
}}
|
|
/>
|
|
)}
|
|
</div>
|
|
</div>
|
|
);
|
|
};
|
|
|
|
export default CasbinEditor;
|