github.com/turbot/steampipe@v1.7.0-rc.0.0.20240517123944-7cef272d4458/ui/dashboard/src/components/dashboards/Text/index.tsx (about) 1 import Error from "../Error"; 2 import gfm from "remark-gfm"; // Support for strikethrough, tables, tasklists and URLs 3 import ReactMarkdown from "react-markdown"; 4 import { BasePrimitiveProps, ExecutablePrimitiveProps } from "../common"; 5 import { classNames } from "../../../utils/styles"; 6 import { PanelDefinition } from "../../../types"; 7 import { registerComponent } from "../index"; 8 9 const getLongPanelClasses = () => { 10 // switch (type) { 11 // case "alert": 12 // return "p-2 border border-alert bg-alert-light border overflow-hidden sm:rounded-md"; 13 // default: 14 return "overflow-hidden sm:rounded-md"; 15 // } 16 }; 17 18 const getShortPanelClasses = () => { 19 // switch (type) { 20 // case "alert": 21 // return "p-2 border border-alert bg-alert-light prose prose-sm sm:rounded-md max-w-none"; 22 // default: 23 return "prose prose-sm sm:rounded-md max-w-none"; 24 // } 25 }; 26 27 export type TextProps = PanelDefinition & 28 BasePrimitiveProps & 29 ExecutablePrimitiveProps & { 30 display_type?: "raw" | "markdown" | "html"; 31 properties: { 32 value: string; 33 }; 34 }; 35 36 const Markdown = ({ value }) => { 37 if (!value) { 38 return null; 39 } 40 41 // Use standard prose styles from Tailwind 42 // Do not restrict width, that's the job of the wrapping panel 43 const isLong = value.split("\n").length > 3; 44 const panelClasses = isLong ? getLongPanelClasses() : getShortPanelClasses(); 45 const proseHeadings = 46 "prose-h1:text-3xl prose-h2:text-2xl prose-h3:text-xl prose-h3:mt-1 p-4"; 47 48 return ( 49 <> 50 {isLong ? ( 51 <div className={panelClasses}> 52 <div 53 className={classNames( 54 "p-2 sm:p-1 prose prose-sm max-w-none break-keep", 55 proseHeadings 56 )} 57 > 58 <ReactMarkdown remarkPlugins={[gfm]}>{value}</ReactMarkdown> 59 </div> 60 </div> 61 ) : ( 62 <article 63 className={classNames(panelClasses, "break-keep", proseHeadings)} 64 > 65 <ReactMarkdown remarkPlugins={[gfm]}>{value}</ReactMarkdown> 66 </article> 67 )} 68 </> 69 ); 70 }; 71 72 const Raw = ({ value }) => { 73 if (!value) { 74 return null; 75 } 76 return <pre className="whitespace-pre-wrap break-keep">{value}</pre>; 77 }; 78 79 const renderText = (type, value) => { 80 switch (type) { 81 case "markdown": 82 return <Markdown value={value} />; 83 case "raw": 84 return <Raw value={value} />; 85 default: 86 return <Error error={`Unsupported text type ${type}`} />; 87 } 88 }; 89 90 const Text = (props: TextProps) => 91 renderText( 92 props.display_type || "markdown", 93 props.properties ? props.properties.value : null 94 ); 95 96 registerComponent("text", Text); 97 98 export default Text;