@beastmode-develeap/beastmode 0.1.366 → 0.1.368

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -15,7 +15,7 @@
15
15
  }
16
16
  </script>
17
17
  <!--BOARD_DATA-->
18
- <script>window.__BUILD_STAMP__ = "20260605-063235-fceeeb5";</script>
18
+ <script>window.__BUILD_STAMP__ = "20260605-085557-99f18b0";</script>
19
19
  <link rel="preconnect" href="https://fonts.googleapis.com">
20
20
  <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
21
21
  <link href="https://fonts.googleapis.com/css2?family=IBM+Plex+Sans:wght@300;400;500;600;700&family=JetBrains+Mono:wght@400;500;600;700&display=swap" rel="stylesheet">
@@ -4281,7 +4281,7 @@ function Sidebar({ currentHash, factoryName, theme, onToggleTheme, selectedProje
4281
4281
  api('GET', '/api/projects')
4282
4282
  .then(data => setProjects(data.projects || []))
4283
4283
  .catch(() => {});
4284
- }, []);
4284
+ }, [selectedProject]);
4285
4285
 
4286
4286
  const links = [
4287
4287
  { path: '#/dashboard', icon: 'dashboard', label: 'Dashboard' },
@@ -8989,8 +8989,8 @@ function ProjectsPage({ selectedProject, onProjectChange }) {
8989
8989
  <div class="card" style="margin-bottom:0;">
8990
8990
  <div class="card-header"><h3>Start from Scratch</h3></div>
8991
8991
  <p style="font-size:13px;color:var(--text-secondary);margin-bottom:12px;">
8992
- Build a new product from an idea. BeastMode guides you through brainstorming,
8993
- PRD, architecture, and creates the project for you.
8992
+ Start a new product from an idea. BeastMode creates a new project for it
8993
+ and guides you through brainstorming, PRD, and architecture.
8994
8994
  </p>
8995
8995
  <button class="btn btn-primary" onclick=${() => navigate('#/new-product')}>
8996
8996
  <${Icon} name="plus" size=${14} />
@@ -10085,6 +10085,7 @@ function SettingsPage() {
10085
10085
  // plus well-known model families. No more hardcoding — when Anthropic
10086
10086
  // releases a new model, it shows up as soon as someone sets it in config.
10087
10087
  const KNOWN_MODELS = [
10088
+ 'claude-opus-4-8',
10088
10089
  'claude-opus-4-7', 'claude-sonnet-4-7',
10089
10090
  'claude-opus-4-6', 'claude-sonnet-4-6',
10090
10091
  'claude-haiku-4-5',
@@ -10617,7 +10618,7 @@ function PhaseProgress({ phases, currentPhase }) {
10617
10618
  `;
10618
10619
  }
10619
10620
 
10620
- function InceptionSetup({ methodologies, onStart, onCancel }) {
10621
+ function InceptionSetup({ methodologies, onStart, onCancel, error }) {
10621
10622
  const [productName, setProductName] = useState('');
10622
10623
  const [idea, setIdea] = useState('');
10623
10624
  const [methodology, setMethodology] = useState('bmad');
@@ -10655,6 +10656,7 @@ function InceptionSetup({ methodologies, onStart, onCancel }) {
10655
10656
  <option value="fully_autonomous">Fully autonomous — generate everything, I approve (2-5 min)</option>
10656
10657
  </select>
10657
10658
  </div>
10659
+ ${error ? html`<div class="error-msg">${error}</div>` : ''}
10658
10660
  <div style="display:flex;gap:8px;justify-content:flex-end;margin-top:16px;">
10659
10661
  <button class="btn" onClick=${onCancel}>Cancel</button>
10660
10662
  <button class="btn btn-primary" disabled=${!productName.trim() || !idea.trim()}
@@ -11159,10 +11161,21 @@ function ToolResultCard({ content, extra }) {
11159
11161
  // Strategy Start Screen — 1-liner prompt or Product inception form
11160
11162
  // ================================================================
11161
11163
 
11162
- function StrategyStartPage({ selectedProject, sessionType }) {
11164
+ // Derive a board/namespace slug from a product name: lowercase, collapse
11165
+ // runs of non-[a-z0-9] to a single hyphen, strip leading/trailing hyphens.
11166
+ function slugifyProduct(name) {
11167
+ return String(name || '')
11168
+ .trim()
11169
+ .toLowerCase()
11170
+ .replace(/[^a-z0-9]+/g, '-')
11171
+ .replace(/^-+|-+$/g, '');
11172
+ }
11173
+
11174
+ function StrategyStartPage({ selectedProject, sessionType, onProjectChange }) {
11163
11175
  const [topic, setTopic] = useState('');
11164
11176
  const [approach, setApproach] = useState('auto');
11165
11177
  const [methodologies, setMethodologies] = useState([]);
11178
+ const [productError, setProductError] = useState('');
11166
11179
 
11167
11180
  useEffect(() => {
11168
11181
  api('GET', '/api/methodologies').then(data => setMethodologies(data.methodologies || [])).catch(() => {});
@@ -11172,17 +11185,40 @@ function StrategyStartPage({ selectedProject, sessionType }) {
11172
11185
  if (sessionType === 'product') {
11173
11186
  return html`<${InceptionSetup}
11174
11187
  methodologies=${methodologies}
11175
- onStart=${(config) => {
11176
- api('POST', '/api/strategy/' + selectedProject + '/sessions', {
11177
- name: config.productName,
11178
- idea: config.idea,
11179
- methodology: config.methodology,
11180
- interactionMode: config.interactionMode,
11181
- sessionType: 'product',
11182
- approach: config.methodology,
11183
- }).then(session => {
11188
+ error=${productError}
11189
+ onStart=${async (config) => {
11190
+ setProductError('');
11191
+ const slug = slugifyProduct(config.productName);
11192
+ if (!slug) {
11193
+ setProductError('Enter a valid product name (letters or numbers).');
11194
+ return;
11195
+ }
11196
+ try {
11197
+ const projData = await api('GET', '/api/projects');
11198
+ const existing = (projData && projData.projects) || [];
11199
+ if (existing.some(p => p.name === slug)) {
11200
+ setProductError("A project named '" + slug + "' already exists — choose a different product name.");
11201
+ return;
11202
+ }
11203
+ await api('POST', '/api/products', {
11204
+ productName: slug,
11205
+ idea: config.idea,
11206
+ methodology: config.methodology,
11207
+ interactionMode: config.interactionMode,
11208
+ });
11209
+ const session = await api('POST', '/api/strategy/' + slug + '/sessions', {
11210
+ name: config.productName,
11211
+ idea: config.idea,
11212
+ methodology: config.methodology,
11213
+ interactionMode: config.interactionMode,
11214
+ sessionType: 'product',
11215
+ approach: config.methodology,
11216
+ });
11217
+ if (onProjectChange) onProjectChange(slug);
11184
11218
  navigate('#/strategy-session/' + session.sessionId);
11185
- });
11219
+ } catch (e) {
11220
+ setProductError('Failed to start product inception: ' + (e && e.message ? e.message : e));
11221
+ }
11186
11222
  }}
11187
11223
  onCancel=${() => navigate('#/strategy')}
11188
11224
  />`;
@@ -12408,7 +12444,7 @@ function App() {
12408
12444
  default:
12409
12445
  if (route.startsWith('#/strategy-start/')) {
12410
12446
  const sessionType = route.replace('#/strategy-start/', '');
12411
- page = html`<${StrategyStartPage} selectedProject=${selectedProject} sessionType=${sessionType} />`;
12447
+ page = html`<${StrategyStartPage} selectedProject=${selectedProject} sessionType=${sessionType} onProjectChange=${setSelectedProject} />`;
12412
12448
  } else if (route.startsWith('#/strategy-session/')) {
12413
12449
  const sessionId = route.replace('#/strategy-session/', '');
12414
12450
  page = html`<${ChatPage} selectedProject=${selectedProject} resumeSession=${sessionId} />`;
@@ -1 +1 @@
1
- fceeeb5904953775795cf5d919b0305b7adb915c
1
+ 99f18b0e925030abe6b5cb06e19d56ee98837350
@@ -1 +1 @@
1
- 20260605-063235-fceeeb5
1
+ 20260605-085557-99f18b0
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@beastmode-develeap/beastmode",
3
- "version": "0.1.366",
3
+ "version": "0.1.368",
4
4
  "description": "BeastMode Dark Factory — turn intent into verified software",
5
5
  "type": "module",
6
6
  "bin": {