Spaces:
Build error
Build error
| import React from "react"; | |
| import { FaArrowRotateRight } from "react-icons/fa6"; | |
| import { FaExternalLinkAlt, FaHome } from "react-icons/fa"; | |
| import { useTranslation } from "react-i18next"; | |
| import { useActiveHost } from "#/hooks/query/use-active-host"; | |
| import { PathForm } from "#/components/features/served-host/path-form"; | |
| import { I18nKey } from "#/i18n/declaration"; | |
| function ServedApp() { | |
| const { t } = useTranslation(); | |
| const { activeHost } = useActiveHost(); | |
| const [refreshKey, setRefreshKey] = React.useState(0); | |
| const [currentActiveHost, setCurrentActiveHost] = React.useState< | |
| string | null | |
| >(null); | |
| const [path, setPath] = React.useState<string>("hello"); | |
| const formRef = React.useRef<HTMLFormElement>(null); | |
| const handleOnBlur = () => { | |
| if (formRef.current) { | |
| const formData = new FormData(formRef.current); | |
| const urlInputValue = formData.get("url")?.toString(); | |
| if (urlInputValue) { | |
| const url = new URL(urlInputValue); | |
| setCurrentActiveHost(url.origin); | |
| setPath(url.pathname); | |
| } | |
| } | |
| }; | |
| const resetUrl = () => { | |
| setCurrentActiveHost(activeHost); | |
| setPath(""); | |
| if (formRef.current) { | |
| formRef.current.reset(); | |
| } | |
| }; | |
| React.useEffect(() => { | |
| resetUrl(); | |
| }, [activeHost]); | |
| const fullUrl = `${currentActiveHost}/${path}`; | |
| if (!currentActiveHost) { | |
| return ( | |
| <div className="flex items-center justify-center w-full h-full p-10"> | |
| <span className="text-neutral-400 font-bold"> | |
| If you tell OpenHands to start a web server, the app will appear here. | |
| </span> | |
| </div> | |
| ); | |
| } | |
| return ( | |
| <div className="h-full w-full"> | |
| <div className="w-full p-2 flex items-center gap-4 border-b border-neutral-600"> | |
| <button | |
| type="button" | |
| onClick={() => window.open(fullUrl, "_blank")} | |
| className="text-sm" | |
| > | |
| <FaExternalLinkAlt className="w-4 h-4" /> | |
| </button> | |
| <button | |
| type="button" | |
| onClick={() => setRefreshKey((prev) => prev + 1)} | |
| className="text-sm" | |
| > | |
| <FaArrowRotateRight className="w-4 h-4" /> | |
| </button> | |
| <button type="button" onClick={() => resetUrl()} className="text-sm"> | |
| <FaHome className="w-4 h-4" /> | |
| </button> | |
| <div className="w-full flex"> | |
| <PathForm | |
| ref={formRef} | |
| onBlur={handleOnBlur} | |
| defaultValue={fullUrl} | |
| /> | |
| </div> | |
| </div> | |
| <iframe | |
| key={refreshKey} | |
| title={t(I18nKey.SERVED_APP$TITLE)} | |
| src={fullUrl} | |
| className="w-full h-full" | |
| /> | |
| </div> | |
| ); | |
| } | |
| export default ServedApp; | |