// Teklens.AI — Workspace (tenant) Settings.
// Opened from the bottom "building" icon on the rail. Looks identical to project
// settings, but is OUTSIDE any project: the side-panel heading reads "Workspace
// Settings" instead of a project name. Integrations are split into one nav entry per
// connector (GitHub / Jira / Confluence), mirroring the project "Data sources" group.
// Reuses globals: Icon, TeklensLogo, SettingsCard, SettingsField, SETTINGS_INPUT, Picker, SettingsToggle.

const WS_NAV = [
  { group: "Workspace", items: [
    { id: "ws-general", label: "Workspace Settings", icon: "building" },
    { id: "ws-members", label: "Team Members", icon: "users" },
    { id: "ws-identities", label: "Identities", icon: "entity" },
  ]},
  { group: "Library", items: [
    { id: "ws-roles", label: "Agents", icon: "users" },
    { id: "ws-agents", label: "Sub-Agents", icon: "robot" },
    { id: "ws-skills", label: "Skills", icon: "puzzle" },
    { id: "ws-artefacts", label: "Artefacts", icon: "file" },
  ]},
  { group: "Integrations", items: [
    { id: "ws-github", label: "GitHub", icon: "branch" },
    { id: "ws-jira", label: "Jira", icon: "jira" },
    { id: "ws-confluence", label: "Confluence", icon: "confluence" },
  ]},
];

const WS_ITEM_SECTIONS = ["ws-skills", "ws-agents", "ws-artefacts", "ws-roles"];

function WorkspaceSettingsSidePanel({ section, onSection, ws }) {
  const drilled = ws && WS_ITEM_SECTIONS.includes(section);
  return (
    <aside className="w-full h-full bg-[var(--surface)] flex flex-col border-r border-[var(--border)]">
      <div className="px-4 h-12 flex items-center shrink-0"><TeklensLogo /></div>
      <div className="h-[9px] shrink-0" />
      {/* heading — workspace, not a project */}
      <div className="px-4 shrink-0">
        <div className="h-12 flex items-center gap-2.5">
          <Icon name="building" size={18} className="text-[var(--accent)] shrink-0" />
          <span className="block text-left text-[17px] font-bold text-[var(--accent)] tracking-[-0.01em] truncate">Workspace Settings</span>
        </div>
      </div>
      <div className="mx-3 mt-1 mb-2 h-px bg-[var(--border)] shrink-0" />
      <div className="flex-1 min-h-0 overflow-y-auto px-3 pb-3">
        {drilled ? (
          <>
            <button onClick={() => onSection("ws-general")} className="flex items-center gap-1.5 px-1.5 py-1.5 mb-2 rounded-md text-[12.5px] font-medium text-[var(--text-muted)] hover:text-[var(--text)] hover:bg-[var(--hover)]">
              <Icon name="chevron-left" size={15} /> Workspace
            </button>
            {section === "ws-skills" && <SkillItems ws={ws} />}
            {section === "ws-agents" && <AgentItems ws={ws} />}
            {section === "ws-roles" && <RoleItems ws={ws} />}
            {section === "ws-artefacts" && <ArtefactItems ws={ws} />}
          </>
        ) : (
          WS_NAV.map((g) => (
            <div key={g.group} className="mb-3.5">
              <div className="px-2 mb-1 text-[10.5px] font-semibold tracking-[0.07em] text-[var(--text-faint2)] uppercase">{g.group}</div>
              <div className="flex flex-col gap-0.5">
                {g.items.map((it) => {
                  const on = section === it.id;
                  const hasItems = WS_ITEM_SECTIONS.includes(it.id);
                  return (
                    <button key={it.id} onClick={() => onSection(it.id)}
                      className={`flex items-center gap-2.5 px-2.5 py-1.5 rounded-lg text-left transition-colors ${on ? "bg-[var(--accent)]/[0.09] text-[var(--accent)]" : "text-[var(--text-2)] hover:bg-[var(--hover)]"}`}>
                      <Icon name={it.icon} size={15} className={on ? "text-[var(--accent)]" : "text-[var(--text-faint2)]"} />
                      <span className="text-[13px] font-medium truncate flex-1">{it.label}</span>
                      {hasItems && <Icon name="chevron-right" size={14} className="shrink-0" style={{ color: "var(--bar)" }} />}
                    </button>
                  );
                })}
              </div>
            </div>
          ))
        )}
      </div>
      <div className="mt-auto border-t border-[var(--border)] px-2 py-2 flex items-center gap-2 shrink-0">
        <img src={window.__res ? window.__res("person-simon.webp") : "person-simon.webp"} alt="Simon" className="w-7 h-7 rounded-full object-cover shrink-0" />
        <div className="flex-1 min-w-0"><div className="text-[12.5px] font-medium truncate">simon@contem.ch</div></div>
        <button className="p-1.5 rounded hover:bg-[var(--hover)] text-[var(--text-3)]"><Icon name="chevron-up-down" size={14} /></button>
      </div>
    </aside>
  );
}

function WSShell({ children, footer }) {
  return (
    <div className="flex-1 min-w-0 overflow-y-auto bg-[var(--surface-2)]">
      <div className="max-w-[680px] mx-auto px-6 pt-12 pb-20">
        <h1 className="text-[26px] font-semibold tracking-tight text-[var(--text)]">Workspace Settings</h1>
        <p className="text-[14px] text-[var(--text-muted)] mt-1">Tenant-wide configuration, integrations, and member management</p>
        <div className="mt-7 flex flex-col gap-6">{children}</div>
        {footer && <div className="mt-6">{footer}</div>}
      </div>
    </div>
  );
}

function WSStatusBadge({ state }) {
  if (state === "connected")
    return <span className="inline-flex items-center gap-1.5 text-[12px] font-semibold px-2.5 py-1 rounded-full" style={{ color: "var(--green-ink)", background: "var(--green-bg)" }}><Icon name="check" size={13} /> Connected</span>;
  return <span className="inline-flex items-center gap-1.5 text-[12px] font-medium px-2.5 py-1 rounded-full text-[var(--text-faint)] bg-[var(--surface-inset)]">Not linked</span>;
}

// Integration card with brand header + status, optional inset key/value facts, and actions.
function WSIntegrationCard({ icon, iconColor, title, subtitle, state, facts, children }) {
  return (
    <div className="rounded-2xl border border-[var(--border-soft)] bg-[var(--card)] p-7 shadow-[0_1px_2px_rgba(0,0,0,0.03)]">
      <div className="flex items-start gap-3">
        <span className="shrink-0 mt-0.5" style={{ color: iconColor }}><Icon name={icon} size={22} /></span>
        <div className="min-w-0 flex-1">
          <div className="text-[16px] font-semibold text-[var(--text)]">{title}</div>
          <p className="text-[13px] text-[var(--text-faint)] mt-0.5 leading-relaxed">{subtitle}</p>
        </div>
        {state && <div className="shrink-0"><WSStatusBadge state={state} /></div>}
      </div>
      {facts && (
        <div className="mt-5 rounded-xl bg-[var(--surface-2)] border border-[var(--border-soft)] px-4 py-3.5 flex flex-col gap-2">
          {facts.map((f, i) => (
            <div key={i} className="text-[13.5px] text-[var(--text-3)]">{f.k}: <span className="font-semibold text-[var(--text)]">{f.v}</span></div>
          ))}
        </div>
      )}
      {children && <div className="mt-5">{children}</div>}
    </div>
  );
}

function WSGhostButton({ children, primary }) {
  return (
    <button className={`px-4 py-2 rounded-lg text-[13px] font-medium ${primary ? "bg-[var(--card)] border border-[var(--border)] text-[var(--text-2)] hover:bg-[var(--surface)]" : "text-[var(--text-2)] hover:bg-[var(--hover)]"}`}>{children}</button>
  );
}

// ---------- pages ----------
function WSGeneral() {
  const [name, setName] = useState("simon@teklens.ch's Workspace");
  return (
    <WSShell>
      <SettingsCard title="Workspace" subtitle="Basic information about your workspace tenant.">
        <SettingsField label="Workspace Name">
          <input value={name} onChange={(e) => setName(e.target.value)} className={SETTINGS_INPUT} />
        </SettingsField>
        <div className="flex">
          <button className="ml-auto px-4 py-2 rounded-lg text-[13px] font-medium text-white bg-[var(--accent)] hover:brightness-110 shadow-[0_1px_0_rgba(0,0,0,0.08)]">Save Changes</button>
        </div>
      </SettingsCard>
    </WSShell>
  );
}

const WS_MEMBERS = [
  { id: "you", name: "simon@contem.ch", you: true, role: "Admin", avatar: "person-simon.webp" },
  { id: "m2", name: "dini@contem.ch", role: "Admin" },
  { id: "m3", name: "lea@contem.ch", role: "Member" },
  { id: "m4", name: "marc@contem.ch", role: "Member" },
];
function WSMembers() {
  const [members, setMembers] = useState(WS_MEMBERS);
  const [email, setEmail] = useState("");
  const [role, setRole] = useState("Member");
  const invite = () => {
    if (!email.trim()) return;
    setMembers((ms) => [...ms, { id: "m" + Date.now().toString(36), name: email.trim(), role }]);
    setEmail("");
  };
  return (
    <WSShell>
      <SettingsCard title="Team Members" subtitle="Manage who has access to this workspace.">
        <div className="flex flex-col divide-y divide-[var(--border-soft)] -mt-1">
          {members.map((m) => (
            <div key={m.id} className="flex items-center gap-3 py-3">
              {m.avatar
                ? <img src={window.__res ? window.__res(m.avatar) : m.avatar} alt={m.name} className="w-8 h-8 rounded-full object-cover shrink-0" />
                : <span className="w-8 h-8 rounded-full bg-[var(--border)] text-[var(--text-muted)] flex items-center justify-center text-[12px] font-semibold shrink-0">{m.name[0].toUpperCase()}</span>}
              <div className="min-w-0 flex-1">
                <div className="text-[13.5px] font-medium text-[var(--text)] truncate">{m.name}{m.you && <span className="text-[var(--text-faint2)] font-normal"> (you)</span>}</div>
              </div>
              <span className={`shrink-0 text-[12px] font-medium px-2.5 py-1 rounded-full ${m.role === "Admin" ? "text-[var(--accent)] bg-[var(--accent)]/[0.1]" : "text-[var(--text-muted)] bg-[var(--surface-inset)]"}`}>{m.role}</span>
              {!m.you && <button className="p-1.5 rounded text-[var(--text-faint2)] hover:text-[var(--amber-ink)] hover:bg-[var(--hover)] shrink-0"><Icon name="x" size={15} /></button>}
            </div>
          ))}
        </div>
        <div className="mt-4 pt-4 border-t border-[var(--border-soft)] flex items-center gap-2.5">
          <input value={email} onChange={(e) => setEmail(e.target.value)} placeholder="Email address" className={SETTINGS_INPUT + " flex-1"} />
          <div className="w-[130px] shrink-0"><Picker value={role} options={["Member", "Admin"]} onChange={setRole} icon="user" /></div>
          <button onClick={invite} title="Invite" className="shrink-0 w-10 h-10 rounded-lg flex items-center justify-center bg-[var(--accent)] text-white hover:brightness-110 shadow-[0_1px_0_rgba(0,0,0,0.08)]"><Icon name="user" size={16} /></button>
        </div>
      </SettingsCard>
    </WSShell>
  );
}

function WSGitHub() {
  return (
    <WSShell>
      <WSIntegrationCard icon="repo" iconColor="var(--text)" title="GitHub" subtitle="Connect a GitHub organization using the GitHub App." state="connected"
        facts={[{ k: "Connected to", v: "Contem-Club" }, { k: "Repositories synced", v: "57" }, { k: "Files indexed", v: "1,354 files indexed" }]}>
        <div className="flex items-center gap-2">
          <WSGhostButton primary>Sync repositories</WSGhostButton>
          <WSGhostButton>Change connection</WSGhostButton>
        </div>
      </WSIntegrationCard>
    </WSShell>
  );
}

// Shared Atlassian connection banner shown on both Jira and Confluence pages.
function AtlassianConnection() {
  return (
    <div className="rounded-xl bg-[var(--surface-2)] border border-[var(--border-soft)] px-4 py-3.5 flex items-center gap-2.5">
      <Icon name="confluence" size={16} className="text-[var(--accent-strong)] shrink-0" />
      <div className="text-[13.5px] text-[var(--text-3)]">Atlassian Cloud · <span className="font-semibold text-[var(--text)]">https://teklens.atlassian.net</span></div>
      <WSStatusBadge state="connected" />
    </div>
  );
}

function WSJira() {
  return (
    <WSShell>
      <WSIntegrationCard icon="jira" iconColor="var(--accent)" title="Jira" subtitle="Connect your Atlassian Cloud instance to sync Jira projects, issues, and sprints." state="connected">
        <div className="flex flex-col gap-4">
          <AtlassianConnection />
          <div className="rounded-xl border border-[var(--border-soft)] px-4 py-3.5">
            <div className="flex items-center gap-2 text-[14px] text-[var(--text)]"><Icon name="jira" size={15} className="text-[var(--accent)]" /> <span className="font-semibold">Jira</span> <span className="text-[var(--text-faint2)] text-[13px]">(2 projects) · 386 issues · 6 sprints</span></div>
            <button className="mt-3 px-3.5 py-2 rounded-lg text-[13px] font-medium bg-[var(--card)] border border-[var(--border)] text-[var(--text-2)] hover:bg-[var(--surface)]">Sync &amp; index projects</button>
          </div>
          <div className="rounded-xl border border-[var(--border-soft)] px-4 py-3.5">
            <div className="flex items-center gap-2 text-[14px] text-[var(--text)]"><Icon name="jira" size={15} className="text-[var(--accent)]" /> <span className="font-semibold">Jira Forge app</span> <WSStatusBadge state="notlinked" /></div>
            <p className="mt-1.5 text-[12.5px] text-[var(--text-faint)]">Open Teklens in Jira to link this site automatically.</p>
          </div>
        </div>
      </WSIntegrationCard>
    </WSShell>
  );
}

function WSConfluence() {
  return (
    <WSShell>
      <WSIntegrationCard icon="confluence" iconColor="var(--accent-strong)" title="Confluence" subtitle="Connect your Atlassian Cloud instance to sync and index Confluence spaces." state="connected">
        <div className="flex flex-col gap-4">
          <AtlassianConnection />
          <div className="rounded-xl border border-[var(--border-soft)] px-4 py-3.5">
            <div className="flex items-center gap-2 text-[14px] text-[var(--text)]"><Icon name="confluence" size={15} className="text-[var(--accent-strong)]" /> <span className="font-semibold">Confluence</span> <span className="text-[var(--text-faint2)] text-[13px]">(6 spaces) · 20 pages</span></div>
            <button className="mt-3 px-3.5 py-2 rounded-lg text-[13px] font-medium bg-[var(--card)] border border-[var(--border)] text-[var(--text-2)] hover:bg-[var(--surface)]">Sync &amp; index spaces</button>
          </div>
        </div>
      </WSIntegrationCard>
    </WSShell>
  );
}

// ---------- Identities — merge people across GitHub / Jira / code / login ----------
const WS_IDENT_SOURCE = {
  github:     { icon: "repo",       label: "GitHub" },
  jira:       { icon: "jira",       label: "Jira" },
  confluence: { icon: "confluence", label: "Confluence" },
  code:       { icon: "code",       label: "Code" },
  login:      { icon: "user",       label: "Login" },
};
const WS_IDENTITIES = [
  { id: "alex000kim", name: "alex000kim", sources: ["github"], identities: 1, status: "active", color: "var(--accent)" },
  { id: "amr", name: "Amr Abulseoud", sources: ["github", "jira"], identities: 2, status: "active", color: "var(--green-ink)" },
  { id: "aronprins", name: "aronprins", sources: ["github"], identities: 1, status: "active", color: "var(--amber-ink)" },
  { id: "cryppadotta", name: "cryppadotta", sources: ["github"], identities: 1, status: "active", color: "var(--pink-ink)" },
  { id: "cursoragent", name: "cursoragent", sources: ["github", "code"], identities: 2, status: "active", color: "var(--text)" },
  { id: "devinfoley", name: "devinfoley", sources: ["github"], identities: 1, status: "active", color: "#e0b65a" },
  { id: "evan-onyx", name: "evan-onyx", sources: ["github"], identities: 1, status: "active", color: "var(--violet-ink)" },
  { id: "gsxdsm", name: "gsxdsm", sources: ["github"], identities: 1, status: "active", color: "var(--violet-ink)" },
  { id: "simon", name: "Simon Brunner", sources: ["github", "jira", "confluence", "login"], identities: 4, status: "active", color: "var(--accent-strong)" },
  { id: "dini", name: "DiNi", sources: ["jira", "login"], identities: 2, status: "active", color: "var(--green-ink)" },
  { id: "henkdz", name: "HenkDz", sources: ["github"], identities: 1, status: "active", color: "var(--text-3)" },
  { id: "iuliana", name: "iuliana-zinceac", sources: ["github"], identities: 1, status: "active", color: "var(--amber-ink)" },
  { id: "jmelahman", name: "jmelahman", sources: ["github"], identities: 1, status: "active", color: "var(--accent)" },
  { id: "legacy-bot", name: "ci-deploy-bot", sources: ["github", "code"], identities: 2, status: "inactive", color: "var(--text-faint2)" },
];

function WSIdentSourcePill({ sys }) {
  const s = WS_IDENT_SOURCE[sys] || WS_IDENT_SOURCE.github;
  return (
    <span className="inline-flex items-center gap-1.5 text-[12px] text-[var(--text-2)] bg-[var(--card)] border border-[var(--border)] rounded-md px-2 py-1">
      <Icon name={s.icon} size={12} className="text-[var(--text-3)]" /> {s.label}
    </span>
  );
}

function WSIdentAvatar({ name, color }) {
  const initials = name.replace(/[^a-zA-Z ]/g, "").split(/\s+/).slice(0, 2).map((w) => w[0]).join("").toUpperCase() || name.slice(0, 2).toUpperCase();
  return <span className="w-8 h-8 rounded-full flex items-center justify-center shrink-0 text-white text-[11px] font-semibold" style={{ background: color }}>{initials}</span>;
}

function WSIdentities() {
  const [query, setQuery] = useState("");
  const [statusFilter, setStatusFilter] = useState("Active");
  const [selected, setSelected] = useState(() => new Set());
  const filtered = WS_IDENTITIES.filter((p) => {
    if (statusFilter === "Active" && p.status !== "active") return false;
    if (statusFilter === "Inactive" && p.status !== "inactive") return false;
    return !query || p.name.toLowerCase().includes(query.toLowerCase());
  });
  const toggle = (id) => setSelected((s) => { const n = new Set(s); n.has(id) ? n.delete(id) : n.add(id); return n; });
  const allShown = filtered.length > 0 && filtered.every((p) => selected.has(p.id));
  const toggleAll = () => setSelected((s) => {
    const n = new Set(s);
    if (allShown) filtered.forEach((p) => n.delete(p.id)); else filtered.forEach((p) => n.add(p.id));
    return n;
  });

  return (
    <div className="flex-1 min-w-0 overflow-y-auto bg-[var(--surface-2)]">
      <div className="max-w-[1000px] mx-auto px-8 pt-12 pb-20">
        <div className="flex items-baseline gap-2.5">
          <h1 className="text-[26px] font-semibold tracking-tight text-[var(--text)]">Identities</h1>
          <span className="text-[16px] text-[var(--text-faint2)]">{filtered.length}</span>
        </div>
        <p className="text-[14px] text-[var(--text-muted)] mt-1">Merge a person's accounts across GitHub, Jira, code, and login into a single identity.</p>

        {/* toolbar */}
        <div className="mt-6 flex items-center gap-2.5">
          <div className="flex-1 flex items-center gap-2 px-3 rounded-lg border border-[var(--border)] bg-[var(--card)] focus-within:border-[var(--accent)]">
            <Icon name="search" size={15} className="text-[var(--text-faint2)] shrink-0" />
            <input value={query} onChange={(e) => setQuery(e.target.value)} placeholder="Search identities…"
              className="flex-1 py-2.5 bg-transparent outline-none text-[14px] text-[var(--text)] placeholder:text-[var(--text-faint2)]" />
          </div>
          <div className="w-[140px] shrink-0"><Picker value={statusFilter} options={["Active", "Inactive", "All"]} onChange={setStatusFilter} icon="filter" /></div>
        </div>

        {/* selection / merge bar */}
        {selected.size >= 2 && (
          <div className="mt-3 flex items-center gap-3 rounded-xl border border-[var(--accent)]/30 bg-[var(--accent)]/[0.06] px-4 py-2.5">
            <Icon name="entity" size={16} className="text-[var(--accent)] shrink-0" />
            <span className="text-[13px] text-[var(--text)] font-medium">{selected.size} identities selected</span>
            <span className="text-[12px] text-[var(--text-muted)]">— merge them into a single person, keeping all source links.</span>
            <div className="ml-auto flex items-center gap-2">
              <button onClick={() => setSelected(new Set())} className="px-3 py-1.5 rounded-lg text-[12.5px] font-medium text-[var(--text-muted)] hover:bg-[var(--hover)]">Clear</button>
              <button className="flex items-center gap-1.5 px-3.5 py-1.5 rounded-lg bg-[var(--accent)] text-white text-[12.5px] font-medium hover:brightness-110 shadow-[0_1px_0_rgba(0,0,0,0.08)]"><Icon name="merge" size={14} /> Merge identities</button>
            </div>
          </div>
        )}

        {/* table */}
        <div className="mt-4 rounded-2xl border border-[var(--border-soft)] bg-[var(--card)] shadow-[0_1px_2px_rgba(0,0,0,0.03)] overflow-hidden">
          <div className="grid grid-cols-[36px_minmax(150px,1.5fr)_minmax(150px,260px)_90px_90px] items-center gap-3 px-4 py-2.5 border-b border-[var(--border-soft)] bg-[var(--surface-2)] text-[11.5px] font-semibold uppercase tracking-[0.04em] text-[var(--text-faint2)]">
            <button onClick={toggleAll} className="flex items-center justify-center">
              <span className={`w-4 h-4 rounded border flex items-center justify-center ${allShown ? "bg-[var(--accent)] border-[var(--accent)]" : "border-[var(--line)] bg-[var(--card)]"}`}>{allShown && <Icon name="check" size={11} className="text-white" />}</span>
            </button>
            <span>Name</span>
            <span>Sources</span>
            <span className="text-right">Identities</span>
            <span className="text-right">Status</span>
          </div>
          {filtered.map((p) => {
            const on = selected.has(p.id);
            return (
              <div key={p.id} className={`grid grid-cols-[36px_minmax(150px,1.5fr)_minmax(150px,260px)_90px_90px] items-center gap-3 px-4 py-2.5 border-b border-[var(--surface-inset)] last:border-b-0 ${on ? "bg-[var(--accent)]/[0.04]" : "hover:bg-[var(--surface-2)]"}`}>
                <button onClick={() => toggle(p.id)} className="flex items-center justify-center">
                  <span className={`w-4 h-4 rounded border flex items-center justify-center ${on ? "bg-[var(--accent)] border-[var(--accent)]" : "border-[var(--line)] bg-[var(--card)]"}`}>{on && <Icon name="check" size={11} className="text-white" />}</span>
                </button>
                <div className="flex items-center gap-2.5 min-w-0">
                  <WSIdentAvatar name={p.name} color={p.color} />
                  <span className="text-[14px] font-medium text-[var(--text)] truncate">{p.name}</span>
                </div>
                <div className="flex flex-wrap items-center gap-1.5">
                  {p.sources.map((s) => <WSIdentSourcePill key={s} sys={s} />)}
                </div>
                <div className="text-right text-[13.5px] text-[var(--text-3)] tabular-nums">{p.identities}</div>
                <div className="flex justify-end">
                  {p.status === "active"
                    ? <span className="text-[11.5px] font-semibold px-2 py-0.5 rounded-full text-white bg-[var(--accent)]">active</span>
                    : <span className="text-[11.5px] font-semibold px-2 py-0.5 rounded-full text-[var(--text-faint)] bg-[var(--surface-inset)]">inactive</span>}
                </div>
              </div>
            );
          })}
          {filtered.length === 0 && <div className="px-4 py-10 text-center text-[13px] text-[var(--text-faint2)]">No identities match your search.</div>}
        </div>
      </div>
    </div>
  );
}

function WorkspaceSettingsArea({ section, ws }) {
  switch (section) {
    case "ws-members": return <WSMembers />;
    case "ws-identities": return <WSIdentities />;
    case "ws-skills": return <SkillsMain ws={ws} />;
    case "ws-agents": return <AgentsMain ws={ws} />;
    case "ws-roles": return ws.roleSel
      ? <RoleEditor ws={ws} role={ws.roles.find((r) => r.id === ws.roleSel) || ws.roles[0]} />
      : <RolesListView ws={ws} />;
    case "ws-artefacts": return <ArtefactMainEditor ws={ws} />;
    case "ws-github": return <WSGitHub />;
    case "ws-jira": return <WSJira />;
    case "ws-confluence": return <WSConfluence />;
    case "ws-general":
    default: return <WSGeneral />;
  }
}
