PageSourceSearch

https://thestreamlinefactory.com/assets/AdminBlog-Bb6k6tmh.js

js thestreamlinefactory.com collected 2026-10-02 00:57:58 UTC 15,208 bytes, 1 lines download raw bytes

1import{r as n,j as e}from"./react-vendor-C-_weJGF.js";import{b as K,u as F,c as N}from"./query-DA-B5yju.js";import{B as i,s as u,a as m}from"./index-sHdJRwRo.js";import{A as S}from"./AdminLayout-83yQHb0s.js";import{I as d}from"./input-DDtkh_8z.js";import{T as W}from"./textarea-COvO_KSb.js";import{R as M,o as Q}from"./RichTextEditor-C2ws_jh9.js";import{F as o}from"./FormField-sjggNfPQ.js";import{S as z}from"./StatusBadge-Bc5Xeqgn.js";import{C as G}from"./ConfirmDialog-DjQv5vKb.js";import{S as H}from"./SeoFields-BO-HitjJ.js";import{u as J,l as Y,E as L,a8 as V,g as X,a2 as Z,a5 as ee,O as te,U as se}from"./icons-BZJMmL1V.js";import"./radix-CMA3xQgM.js";import"./supabase-BppBjPB2.js";import"./motion-CfmjrLVm.js";import"./logo-BWhOaj1e.js";import"./switch-DmVMlHO-.js";function je(){const p=K(),[C,f]=n.useState(null),[q,b]=n.useState(!1),[_,T]=n.useState(""),[j,U]=n.useState("all"),{data:h=[]}=F({queryKey:["admin-blog-posts"],queryFn:async()=>{const{data:t}=await u.from("blog_posts").select("*, blog_categories(name)").order("created_at",{ascending:!1});return t||[]}}),{data:E=[]}=F({queryKey:["admin-categories"],queryFn:async()=>{const{data:t}=await u.from("blog_categories").select("*").order("name");return t||[]}}),y=h.filter(t=>{const s=t.title.toLowerCase().includes(_.toLowerCase())||t.slug.toLowerCase().includes(_.toLowerCase()),r=j==="all"||t.status===j;return s&&r}),v=N({mutationFn:async t=>{if(t.id){const{error:s}=await u.from("blog_posts").update(t).eq("id",t.id);if(s)throw s}else{const{error:s}=await u.from("blog_posts").insert(t);if(s)throw s}},onSuccess:()=>{p.invalidateQueries({queryKey:["admin-blog-posts"]}),f(null),b(!1),m.success("Post saved!")},onError:()=>m.error("Failed to save post")}),$=N({mutationFn:async t=>{const{error:s}=await u.from("blog_posts").delete().eq("id",t);if(s)throw s},onSuccess:()=>{p.invalidateQueries({queryKey:["admin-blog-posts"]}),m.success("Post deleted")}}),A=N({mutationFn:async({id:t,status:s})=>{const r=s==="published"?"draft":"published",c={status:r};r==="published"&&(c.published_at=new Date().toISOString());const{error:g}=await u.from("blog_posts").update(c).eq("id",t);if(g)throw g},onSuccess:()=>{p.invalidateQueries({queryKey:["admin-blog-posts"]}),m.success("Status updated")}}),P=({post:t})=>{const[s,r]=n.useState({title:t.title||"",slug:t.slug||"",excerpt:t.excerpt||"",content:t.content||"",featured_image_url:t.featured_image_url||"",category_id:t.category_id||"",author_name:t.author_name||"Streamline Factory",status:t.status||"draft",scheduled_publish_at:t.scheduled_publish_at?new Date(new Date(t.scheduled_publish_at).getTime()-new Date().getTimezoneOffset()*6e4).toISOString().slice(0,16):"",seo_title:t.seo_title||"",seo_description:t.seo_description||"",og_title:t.og_title||"",og_description:t.og_description||"",og_image_url:t.og_image_url||"",twitter_title:t.twitter_title||"",twitter_description:t.twitter_description||"",twitter_image_url:t.twitter_image_url||"",canonical_url:t.canonical_url||"",noindex:t.noindex||!1,nofollow:t.nofollow||!1,tags:(t.tags||[]).join(", "),...t.id?{id:t.id}:{}}),[c,g]=n.useState("details"),k=n.useRef(null),[w,D]=n.useState(!1),I=async a=>{D(!0);try{const l=await Q(a,{maxWidth:1600,folder:"blog/featured"});r(O=>({...O,featured_image_url:l.url}));const x=Math.max(0,Math.round((l.originalSize-l.optimizedSize)/1024));m.success(`Image optimized to WebP (${l.width}×${l.height}, saved ${x} KB)`)}catch(l){m.error((l==null?void 0:l.message)||"Failed to upload image")}finally{D(!1)}},B=()=>{const a={...s,tags:s.tags.split(",").map(l=>l.trim()).filter(Boolean),category_id:s.category_id||null,scheduled_publish_at:s.scheduled_publish_at?new Date(s.scheduled_publish_at).toISOString():null};a.status==="published"&&!t.published_at&&(a.published_at=new Date().toISOString()),a.scheduled_publish_at&&new Date(a.scheduled_publish_at)>new Date&&(a.status="draft"),v.mutate(a)},R=()=>{!s.slug&&s.title&&r({...s,slug:s.title.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-|-$/g,"")})};return e.jsxs("div",{className:"space-y-6",children:[e.jsxs("div",{className:"flex items-center justify-between",children:[e.jsx("h2",{className:"font-display font-semibold text-xl",children:t.id?"
1Edit Post":"New Blog Post"}),e.jsxs("div",{className:"flex gap-2 items-center",children:[s.slug&&e.jsx(i,{variant:"outline",size:"sm",asChild:!0,children:e.jsxs("a",{href:`/blog/${s.slug}`,target:"_blank",rel:"noopener noreferrer",children:[e.jsx(L,{className:"w-3.5 h-3.5 mr-1"})," Preview"]})}),e.jsx(z,{status:s.status})]})]}),e.jsxs("div",{className:"flex gap-1 bg-secondary rounded-lg p-1",children:[e.jsx("button",{onClick:()=>g("details"),className:`flex-1 px-4 py-2 rounded-md text-sm font-medium transition-colors ${c==="details"?"bg-card text-foreground shadow-sm":"text-muted-foreground hover:text-foreground"}`,children:"Post Details"}),e.jsx("button",{onClick:()=>g("seo"),className:`flex-1 px-4 py-2 rounded-md text-sm font-medium transition-colors ${c==="seo"?"bg-card text-foreground shadow-sm":"text-muted-foreground hover:text-foreground"}`,children:"SEO & Sharing"})]}),c==="details"?e.jsxs(e.Fragment,{children:[e.jsxs("div",{className:"bg-card border border-border rounded-lg p-5 space-y-4",children:[e.jsx("h3",{className:"font-display font-medium text-sm text-muted-foreground uppercase tracking-wide",children:"Post Details"}),e.jsxs("div",{className:"grid grid-cols-1 md:grid-cols-2 gap-4",children:[e.jsx(o,{label:"Title",hint:"The headline of your blog post. Be descriptive and engaging.",required:!0,children:e.jsx(d,{value:s.title,onChange:a=>r({...s,title:a.target.value}),onBlur:R,className:"bg-secondary",placeholder:"e.g. How to Streamline Your Insurance Workflow"})}),e.jsx(o,{label:"URL Slug",hint:"Auto-generated from the title. This forms the post URL: /blog/your-slug",required:!0,children:e.jsx(d,{value:s.slug,onChange:a=>r({...s,slug:a.target.value}),className:"bg-secondary",placeholder:"e.g. streamline-insurance-workflow"})})]}),e.jsxs(o,{label:"Short Summary",hint:"A brief summary (1–2 sentences) shown on the blog listing page and in search results. Aim for 120–160 characters.",children:[e.jsx(W,{value:s.excerpt,onChange:a=>r({...s,excerpt:a.target.value}),className:"bg-secondary",rows:2,placeholder:"Write a brief summary of this post...",maxLength:300}),e.jsxs("p",{className:"text-[11px] text-muted-foreground/60 mt-1",children:[s.excerpt.length,"/300 characters"]})]})]}),e.jsxs("div",{className:"bg-card border border-border rounded-lg p-5 space-y-4",children:[e.jsx("h3",{className:"font-display font-medium text-sm text-muted-foreground uppercase tracking-wide",children:"Post Content"}),e.jsx("p",{className:"text-xs text-muted-foreground -mt-2",children:"Write your full blog post here. Use the toolbar to format text, add headings, lists, links, and quotes."}),e.jsx(o,{label:"Content",children:e.jsx(M,{content:s.content,onChange:a=>r({...s,content:a})})})]}),e.jsxs("div",{className:"bg-card border border-border rounded-lg p-5 space-y-4",children:[e.jsx("h3",{className:"font-display font-medium text-sm text-muted-foreground uppercase tracking-wide",children:"Image & Category"}),e.jsxs(o,{label:"Featured Image URL",hint:"The main image for this post. Upload in Media Library first, then paste the URL here.",children:[e.jsxs("div",{className:"flex gap-2",children:[e.jsx(d,{value:s.featured_image_url,onChange:a=>r({...s,featured_image_url:a.target.value}),className:"bg-secondary flex-1",placeholder:"https://... or upload below"}),e.jsxs(i,{type:"button",variant:"outline",size:"sm",onClick:()=>{var a;return(a=k.current)==null?void 0:a.click()},disabled:w,children:[w?e.jsx(te,{className:"w-4 h-4 mr-1 animate-spin"}):e.jsx(se,{className:"w-4 h-4 mr-1"}),w?"Optimizing...":"Upload JPG/PNG"]}),e.jsx("input",{ref:k,type:"file",accept:"image/jpeg,image/png,image/webp",className:"hidden",onChange:a=>{var x;const l=(x=a.target.files)==null?void 0:x[0];l&&I(l),a.target.value=""}})]}),s.featured_image_url&&e.jsx("div",{className:"mt-2 rounded-md overflow-hidden border border-border max-w-xs",children:e.jsx("img",{src:s.featured_image_url,alt:"Featured preview",className:"w-full h-auto"})}),e.jsx("p",{className:"text-[11px] text-muted-foreground/60 mt-1",children:"📐 Recommended: 1200 × 630 px (1.9:1 landscape). Uploads are auto-converted to WebP and resized to max 1600 px wide."})]}),e.jsxs("div",{className:"grid grid-cols-1 md:grid-cols-2 gap-4",children:[e.jsx(o,{label:"Category",hint:"Assign a category to help readers find related content.",children:e.jsxs("select",{value:s.category_id,onChange:a=>r({...s,category_id:a.target.value}),className:"w-full bg-secondary border border-border rounded-md px-3 py-2 text-sm",children:[e.jsx("option",{value:"",children:"No category"}),E.map(a=>e.jsx("option",{value:a.id,children:a.name},a.id))]})}),e.jsx(o,{label:"Tags",hint:"Comma-separated tags for filtering. e.g. 'insurance, automation, workflow'",children:e.jsx(d,{value:s.tags,onChange:a=>r({...s,tags:a.target.value}),className:"bg-secondary",placeholder:"e.g. insurance, automation"})})]})]}),e.jsxs("div",{className:"bg-card border border-border rounded-lg p-5 space-y-4",children:[e.jsx("h3",{className:"font-display font-medium text-sm text-muted-foreground uppercase tracking-wide",children:"Publishing"}),e.jsxs("div",{className:"grid grid-cols-1 md:grid-cols-2 gap-4",children:[e.jsx(o,{label:"Author Name",hint:"The name displayed as the post author.",children:e.jsx(d,{value:s.author_name,onChange:a=>r({...s,author_name:a.target.value}),className:"bg-secondary"})}),e.jsx(o,{label:"Status",hint:"Draft posts are only visible to admins. Published posts appear on the blog page.",children:e.jsxs("select",{value:s.status,onChange:a=>r({...s,status:a.target.value}),className:"w-full bg-secondary border border-border rounded-md px-3 py-2 text-sm",children:[e.jsx("option",{value:"draft",children:"Draft, not visible to visitors"}),e.jsx("option",{value:"published",children:"Published, live on blog"})]})})]}),e.jsxs(o,{label:"Schedule Publish (optional)",hint:"Set a future date and time to automatically publish this post. Leave blank to publish manually. Uses your local timezone.",children:[e.jsxs("div",{className:"flex gap-2 items-center",children:[e.jsx(d,{type:"datetime-local",value:s.scheduled_publish_at,onChange:a=>r({...s,scheduled_publish_at:a.target.value}),className:"bg-secondary max-w-xs"}),s.scheduled_publish_at&&e.jsx(i,{type:"button",variant:"ghost",size:"sm",onClick:()=>r({...s,scheduled_publish_at:""}),children:"Clear"})]}),s.scheduled_publish_at&&new Date(s.scheduled_publish_at)>new Date&&e.jsxs("p",{className:"text-[11px] text-primary mt-1",children:["⏱ Will auto-publish on ",new Date(s.scheduled_publish_at).toLocaleStr
1ing()," (saved as Draft until then)."]})]})]})]}):e.jsx(H,{data:{seo_title:s.seo_title,seo_description:s.seo_description,og_title:s.og_title,og_description:s.og_description,og_image_url:s.og_image_url,twitter_title:s.twitter_title,twitter_description:s.twitter_description,twitter_image_url:s.twitter_image_url,canonical_url:s.canonical_url,noindex:s.noindex,nofollow:s.nofollow},onChange:a=>r({...s,...a}),defaults:{title:s.title,description:s.excerpt,image:s.featured_image_url,slug:`blog/${s.slug}`}}),e.jsxs("div",{className:"flex gap-2",children:[e.jsx(i,{onClick:B,disabled:v.isPending,children:v.isPending?"Saving...":"Save Post"}),e.jsx(i,{variant:"ghost",onClick:()=>{f(null),b(!1)},children:"Cancel"})]})]})};return C?e.jsx(S,{children:e.jsx(P,{post:C})}):q?e.jsx(S,{children:e.jsx(P,{post:{}})}):e.jsxs(S,{children:[e.jsxs("div",{className:"flex items-center justify-between mb-6",children:[e.jsxs("div",{children:[e.jsx("h1",{className:"font-display text-2xl font-bold",children:"Blog Posts"}),e.jsxs("p",{className:"text-sm text-muted-foreground mt-1",children:["Create, edit, and manage your blog articles. ",h.length," total post",h.length!==1?"s":"","."]})]}),e.jsxs(i,{onClick:()=>b(!0),children:[e.jsx(J,{className:"w-4 h-4 mr-1"})," New Post"]})]}),e.jsxs("div",{className:"flex flex-col sm:flex-row gap-2 mb-4",children:[e.jsxs("div",{className:"relative flex-1",children:[e.jsx(Y,{className:"absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-muted-foreground"}),e.jsx(d,{placeholder:"Search posts...",value:_,onChange:t=>T(t.target.value),className:"pl-10 bg-secondary"})]}),e.jsx("div",{className:"flex gap-1",children:["all","published","draft"].map(t=>e.jsx("button",{onClick:()=>U(t),className:`px-3 py-1.5 rounded-full text-xs font-medium transition-colors ${j===t?"bg-primary text-primary-foreground":"bg-secondary text-muted-foreground hover:text-foreground"}`,children:t==="all"?"All":t==="published"?"Published":"Drafts"},t))})]}),y.length===0&&h.length===0?e.jsxs("div",{className:"text-center py-16 text-muted-foreground bg-card border border-border rounded-lg",children:[e.jsx("p",{className:"font-medium",children:"No blog posts yet"}),e.jsx("p",{className:"text-sm mt-1",children:"Create your first post to start publishing content."})]}):y.length===0?e.jsx("div",{className:"text-center py-8 text-muted-foreground",children:"No posts match your search."}):e.jsx("div",{className:"space-y-2",children:y.map(t=>{var s;return e.jsxs("div",{className:"bg-card border border-border rounded-lg p-4 flex items-center justify-between hover:border-border/80 transition-colors",children:[e.jsxs("div",{className:"flex items-center gap-3 min-w-0",children:[t.featured_image_url&&e.jsx("div",{className:"w-12 h-12 rounded-md overflow-hidden bg-secondary shrink-0",children:e.jsx("img",{src:t.featured_image_url,alt:"",className:"w-full h-full object-cover"})}),e.jsxs("div",{className:"min-w-0",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("h3",{className:"font-semibold text-sm truncate",children:t.title}),e.jsx(z,{status:t.status})]}),e.jsxs("p",{className:"text-xs text-muted-foreground mt-0.5 truncate",children:["/",t.slug," · ",t.author_name,((s=t.blog_categories)==null?void 0:s.name)&&` · ${t.blog_categories.name}`]}),t.status==="draft"&&t.scheduled_publish_at&&new Date(t.scheduled_publish_at)>new Date&&e.jsxs("p",{className:"text-[11px] text-primary mt-0.5 truncate",children:["⏱ Scheduled for ",new Date(t.scheduled_publish_at).toLocaleString()]})]})]}),e.jsxs("div",{className:"flex gap-1 shrink-0",children:[e.jsx(i,{variant:"ghost",size:"sm",asChild:!0,title:"Preview post",children:e.jsx("a",{href:`/blog/${t.slug}`,target:"_blank",rel:"noopener noreferrer",children:e.jsx(L,{className:"w-4 h-4"})})}),e.jsx(i,{variant:"ghost",size:"sm",onClick:()=>A.mutate({id:t.id,status:t.status}),title:t.status==="published"?"Unpublish":"Publish",children:t.status==="published"?e.jsx(V,{className:"w-4 h-4"}):e.jsx(X,{className:"w-4 h-4"})}),e.jsx(i,{variant:"ghost",size:"sm",onClick:()=>f(t),title:"Edit post",children:e.jsx(Z,{className:"w-4 h-4"})}),e.jsx(G,{title:"Delete this blog post?",description:`"${t.title}" will be permanently removed. This action cannot be undone.`,onConfirm:()=>$.mutate(t.id),trigger:e.jsx(i,{variant:"ghost",size:"sm",title:"Delete post",children:e.jsx(ee,{className:"w-4 h-4 text-destructive"})})})]})]},t.id)})})]})}export{je as default};

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.