Skip to content
Open
Show file tree
Hide file tree
Changes from 12 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions kits/fablens/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
.lamatic/
node_modules/
.env
.env.local
46 changes: 46 additions & 0 deletions kits/fablens/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
# FabLens — Eco-Friendly & Skin-Safe Fabric Checker

FabLens lets consumers paste any clothing product URL and instantly understand what materials it's made of — and what that means for their skin and the planet.

No scores. No guilt. Just facts.

## What It Does

- Scrapes the product page for listed materials
- Analyzes each material for environmental impact (biodegradable, water usage, chemical processing)
- Analyzes each material for skin safety (breathability, irritation risk)
- Shows positives and negatives transparently
- Uses a local material database for known fabrics, with AI fallback for unknown ones

## Tech Stack

- **Lamatic AI** — flow orchestration + scraping + LLM analysis
- **Firecrawl** — webpage scraping
- **Next.js** — frontend
- **Tailwind CSS** — styling
- **Groq (llama-4-scout)** — AI model

## Setup

```bash
cd kits/fablens/apps
cp .env.example .env.local
# Add your LAMATIC_API_KEY
npm install
npm run dev
```

## Environment Variables

| Variable | Description |
|----------|-------------|
| `LAMATIC_API_KEY` | Your Lamatic API key from studio.lamatic.ai |

Comment on lines +44 to +52
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Mission-critical docs gap: add FABLENS_WORKFLOW_ID to environment variables.

The setup table is incomplete; users can miss a required config and fail runtime setup.

Proposed patch
 | Variable | Description |
 |----------|-------------|
 | `LAMATIC_API_KEY` | Your Lamatic API key from studio.lamatic.ai |
+| `FABLENS_WORKFLOW_ID` | Workflow ID used by the FabLens Lamatic step |
As per coding guidelines, "Every kit must have a `README.md` that documents setup, environment variables, and usage".
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
## Environment Variables
| Variable | Description |
|----------|-------------|
| `LAMATIC_API_KEY` | Your Lamatic API key from studio.lamatic.ai |
## Environment Variables
| Variable | Description |
|----------|-------------|
| `LAMATIC_API_KEY` | Your Lamatic API key from studio.lamatic.ai |
| `FABLENS_WORKFLOW_ID` | Workflow ID used by the FabLens Lamatic step |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@kits/fablens/README.md` around lines 33 - 38, Update the Environment
Variables table in kits/fablens/README.md to include the missing
FABLENS_WORKFLOW_ID entry: add a new row with `FABLENS_WORKFLOW_ID` as the
Variable and a brief Description (e.g., "Workflow ID used by FabLens to select
the processing workflow") so the README documents all required runtime
configuration alongside `LAMATIC_API_KEY`; ensure formatting matches the
existing Markdown table style.

Comment on lines +46 to +52
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Mission docs sync: add the scoring workflow env var to setup table.

LAMATIC_SCORING_WORKFLOW_ID exists in .env.example but is missing here, so operators can under-configure deployments.

📝 Proposed patch
 | `LAMATIC_API_KEY` | Your Lamatic API key from studio.lamatic.ai |
 | `LAMATIC_PROJECT_ID` | Your Lamatic project ID |
 | `LAMATIC_WORKFLOW_ID` | Workflow ID used for material extraction |
+| `LAMATIC_SCORING_WORKFLOW_ID` | Workflow ID used for unknown-material scoring fallback |
 | `LAMATIC_HOST` | Your Lamatic GraphQL endpoint (e.g. https://<org>.lamatic.dev/graphql) |

As per coding guidelines, "Every kit must have a README.md that documents setup, environment variables, and usage".

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@kits/fablens/README.md` around lines 46 - 52, Add the missing environment
variable LAMATIC_SCORING_WORKFLOW_ID to the README's environment variables table
so operators see it alongside LAMATIC_API_KEY, LAMATIC_PROJECT_ID,
LAMATIC_WORKFLOW_ID, and LAMATIC_HOST; update the table row for
`LAMATIC_SCORING_WORKFLOW_ID` with a short description like "Scoring workflow ID
used for model scoring/validation" to match `.env.example` and ensure README
setup docs list all vars referenced by the kit.

## Supported Sites
Works best with product pages listing materials in plain text (BIBA, Patagonia, independent brands). Sites with scraper protection (H&M, Amazon) may return no results — known v1 limitation.

## Future Plans
- Furniture and cosmetics support
- Image-based material detection
- Percentage-weighted scoring
- Expanded material database
Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated
60 changes: 60 additions & 0 deletions kits/fablens/agent.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
# FabLens

## Overview

FabLens is an intelligent consumer tool that helps users make informed clothing purchases by analyzing textile materials from product URLs. It provides a factual, transparent breakdown of environmental impact and skin safety so users can better understand what a garment is made of and what that means in practical terms. [file:2][file:4]

## Purpose

FabLens exists to make fabric information easier to understand. Many fashion product pages mention materials without explaining their real-world implications, so FabLens translates those materials into clear insights about biodegradability, chemical processing, breathability, and irritation risk. [file:2][file:4]

## Flows

### Material Analysis Flow

- **Trigger:** The user pastes a clothing product URL into the FabLens interface. [file:2]
- **Process:** FabLens scrapes the product page, extracts listed material information, checks known fabrics against a local material database, and uses AI fallback analysis for unknown materials. [file:2]
- **Response:** The system returns a structured explanation of each material’s environmental characteristics and skin-safety considerations, including both positives and negatives. [file:2]
- **Dependencies:** This flow depends on Lamatic orchestration, Firecrawl scraping, and the configured AI model. [file:2]

## Guardrails

- FabLens should present factual information, not moral judgments or guilt-based messaging. [file:2]
- FabLens should not assign simplistic scores when the product goal is transparent explanation. [file:2]
- FabLens should clearly distinguish between known material database results and AI fallback analysis. [file:2]
- FabLens should avoid making unsupported claims when the source page does not provide enough material detail. [file:2]

## Integration Reference

FabLens uses Lamatic AI for flow orchestration and analysis, Firecrawl for webpage scraping, Next.js for the frontend application, Tailwind CSS for styling, and Groq with `llama-4-scout` as the language model layer. [file:2]

## Environment Setup

The application requires a Lamatic API key for operation, and the kit configuration also defines a workflow environment key named `FABLENS_WORKFLOW_ID`. [file:2][file:4]

### Required Environment Variables

| Variable | Description |
|---|---|
| `LAMATIC_API_KEY` | Your Lamatic API key from Lamatic Studio. [file:2] |
| `FABLENS_WORKFLOW_ID` | The workflow ID used by the configured Lamatic kit step. [file:4] |

## Quickstart

1. Navigate to `kits/fablens/apps`. [file:2]
2. Copy `.env.example` to `.env.local`. [file:2]
3. Add your `LAMATIC_API_KEY`. [file:2]
4. Install dependencies with `npm install`. [file:2]
5. Start the development server with `npm run dev`. [file:2]

## Common Failure Modes

| Symptom | Likely Cause | Fix |
|---|---|---|
| No material analysis returned | The target site does not list material information clearly. [file:2] | Try a product page that includes fabric details in plain text. [file:2] |
| No scrape results | The target site has scraper protection. [file:2] | Test with supported or simpler sites such as independent brands. [file:2] |
| Flow does not run correctly | Missing API key or workflow configuration. [file:2][file:4] | Verify `LAMATIC_API_KEY` and `FABLENS_WORKFLOW_ID` are set correctly. [file:2][file:4] |

## Scope

FabLens is currently designed for clothing product pages and works best on sites that expose material details in readable text. Support for furniture, cosmetics, image-based material detection, percentage-weighted scoring, and a larger material database are planned for future versions. [file:2]
Comment on lines +5 to +60
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Mission cleanup: remove unresolved [file:*] reference artifacts.

These labels are undefined (MD052) and render as broken references; also add a single trailing newline at EOF (MD047).

Proposed direction
-FabLens is an intelligent consumer tool ... practical terms. [file:2][file:4]
+FabLens is an intelligent consumer tool ... practical terms.

Apply the same cleanup for all [file:2] / [file:4] occurrences across this document.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
FabLens is an intelligent consumer tool that helps users make informed clothing purchases by analyzing textile materials from product URLs. It provides a factual, transparent breakdown of environmental impact and skin safety so users can better understand what a garment is made of and what that means in practical terms. [file:2][file:4]
## Purpose
FabLens exists to make fabric information easier to understand. Many fashion product pages mention materials without explaining their real-world implications, so FabLens translates those materials into clear insights about biodegradability, chemical processing, breathability, and irritation risk. [file:2][file:4]
## Flows
### Material Analysis Flow
- **Trigger:** The user pastes a clothing product URL into the FabLens interface. [file:2]
- **Process:** FabLens scrapes the product page, extracts listed material information, checks known fabrics against a local material database, and uses AI fallback analysis for unknown materials. [file:2]
- **Response:** The system returns a structured explanation of each materials environmental characteristics and skin-safety considerations, including both positives and negatives. [file:2]
- **Dependencies:** This flow depends on Lamatic orchestration, Firecrawl scraping, and the configured AI model. [file:2]
## Guardrails
- FabLens should present factual information, not moral judgments or guilt-based messaging. [file:2]
- FabLens should not assign simplistic scores when the product goal is transparent explanation. [file:2]
- FabLens should clearly distinguish between known material database results and AI fallback analysis. [file:2]
- FabLens should avoid making unsupported claims when the source page does not provide enough material detail. [file:2]
## Integration Reference
FabLens uses Lamatic AI for flow orchestration and analysis, Firecrawl for webpage scraping, Next.js for the frontend application, Tailwind CSS for styling, and Groq with `llama-4-scout` as the language model layer. [file:2]
## Environment Setup
The application requires a Lamatic API key for operation, and the kit configuration also defines a workflow environment key named `FABLENS_WORKFLOW_ID`. [file:2][file:4]
### Required Environment Variables
| Variable | Description |
|---|---|
| `LAMATIC_API_KEY` | Your Lamatic API key from Lamatic Studio. [file:2] |
| `FABLENS_WORKFLOW_ID` | The workflow ID used by the configured Lamatic kit step. [file:4] |
## Quickstart
1. Navigate to `kits/fablens/apps`. [file:2]
2. Copy `.env.example` to `.env.local`. [file:2]
3. Add your `LAMATIC_API_KEY`. [file:2]
4. Install dependencies with `npm install`. [file:2]
5. Start the development server with `npm run dev`. [file:2]
## Common Failure Modes
| Symptom | Likely Cause | Fix |
|---|---|---|
| No material analysis returned | The target site does not list material information clearly. [file:2] | Try a product page that includes fabric details in plain text. [file:2] |
| No scrape results | The target site has scraper protection. [file:2] | Test with supported or simpler sites such as independent brands. [file:2] |
| Flow does not run correctly | Missing API key or workflow configuration. [file:2][file:4] | Verify `LAMATIC_API_KEY` and `FABLENS_WORKFLOW_ID` are set correctly. [file:2][file:4] |
## Scope
FabLens is currently designed for clothing product pages and works best on sites that expose material details in readable text. Support for furniture, cosmetics, image-based material detection, percentage-weighted scoring, and a larger material database are planned for future versions. [file:2]
FabLens is an intelligent consumer tool that helps users make informed clothing purchases by analyzing textile materials from product URLs. It provides a factual, transparent breakdown of environmental impact and skin safety so users can better understand what a garment is made of and what that means in practical terms.
## Purpose
FabLens exists to make fabric information easier to understand. Many fashion product pages mention materials without explaining their real-world implications, so FabLens translates those materials into clear insights about biodegradability, chemical processing, breathability, and irritation risk.
## Flows
### Material Analysis Flow
- **Trigger:** The user pastes a clothing product URL into the FabLens interface.
- **Process:** FabLens scrapes the product page, extracts listed material information, checks known fabrics against a local material database, and uses AI fallback analysis for unknown materials.
- **Response:** The system returns a structured explanation of each material's environmental characteristics and skin-safety considerations, including both positives and negatives.
- **Dependencies:** This flow depends on Lamatic orchestration, Firecrawl scraping, and the configured AI model.
## Guardrails
- FabLens should present factual information, not moral judgments or guilt-based messaging.
- FabLens should not assign simplistic scores when the product goal is transparent explanation.
- FabLens should clearly distinguish between known material database results and AI fallback analysis.
- FabLens should avoid making unsupported claims when the source page does not provide enough material detail.
## Integration Reference
FabLens uses Lamatic AI for flow orchestration and analysis, Firecrawl for webpage scraping, Next.js for the frontend application, Tailwind CSS for styling, and Groq with `llama-4-scout` as the language model layer.
## Environment Setup
The application requires a Lamatic API key for operation, and the kit configuration also defines a workflow environment key named `FABLENS_WORKFLOW_ID`.
### Required Environment Variables
| Variable | Description |
|---|---|
| `LAMATIC_API_KEY` | Your Lamatic API key from Lamatic Studio. |
| `FABLENS_WORKFLOW_ID` | The workflow ID used by the configured Lamatic kit step. |
## Quickstart
1. Navigate to `kits/fablens/apps`.
2. Copy `.env.example` to `.env.local`.
3. Add your `LAMATIC_API_KEY`.
4. Install dependencies with `npm install`.
5. Start the development server with `npm run dev`.
## Common Failure Modes
| Symptom | Likely Cause | Fix |
|---|---|---|
| No material analysis returned | The target site does not list material information clearly. | Try a product page that includes fabric details in plain text. |
| No scrape results | The target site has scraper protection. | Test with supported or simpler sites such as independent brands. |
| Flow does not run correctly | Missing API key or workflow configuration. | Verify `LAMATIC_API_KEY` and `FABLENS_WORKFLOW_ID` are set correctly. |
## Scope
FabLens is currently designed for clothing product pages and works best on sites that expose material details in readable text. Support for furniture, cosmetics, image-based material detection, percentage-weighted scoring, and a larger material database are planned for future versions.
🧰 Tools
🪛 markdownlint-cli2 (0.22.1)

[warning] 5-5: Reference links and images should use a label that is defined
Missing link or image reference definition: "file"

(MD052, reference-links-images)


[warning] 9-9: Reference links and images should use a label that is defined
Missing link or image reference definition: "file"

(MD052, reference-links-images)


[warning] 33-33: Reference links and images should use a label that is defined
Missing link or image reference definition: "file"

(MD052, reference-links-images)


[warning] 56-56: Reference links and images should use a label that is defined
Missing link or image reference definition: "file"

(MD052, reference-links-images)


[warning] 56-56: Reference links and images should use a label that is defined
Missing link or image reference definition: "file"

(MD052, reference-links-images)


[warning] 60-60: Files should end with a single newline character

(MD047, single-trailing-newline)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@kits/fablens/agent.md` around lines 5 - 60, Remove all unresolved artifact
references like "[file:2]" and "[file:4]" throughout the FabLens README (e.g.,
within the "FabLens" intro, "Purpose", "Material Analysis Flow", "Environment
Setup", "Required Environment Variables", "Quickstart", "Common Failure Modes",
and "Scope" sections) and ensure the file ends with a single trailing newline;
keep the surrounding text intact and preserve variable names such as
LAMATIC_API_KEY and FABLENS_WORKFLOW_ID and section headings while deleting only
the bracketed file tokens.

1 change: 1 addition & 0 deletions kits/fablens/apps/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
LAMATIC_API_KEY=your_lamatic_api_key_here
223 changes: 223 additions & 0 deletions kits/fablens/apps/app/api/analyze/route.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,223 @@
import { materialDB } from "../../../lib/materialDB";

function normalizeMaterial(raw: string): string {
return raw
.toLowerCase()
.replace(/\d+%\s*/g, "")
.replace(/recycled\s*/g, "")
.trim();
}
Comment thread
coderabbitai[bot] marked this conversation as resolved.

function safeJSONParse(raw: any) {
try {
if (typeof raw === "object") return raw;
return JSON.parse(raw.replace(/```json|```/g, "").trim());
} catch {
return null;
}
}

function splitCompound(mat: string): string[] {
const compounds: Record<string, string[]> = {
"viscose rayon": ["viscose", "rayon"],
"rayon viscose": ["viscose", "rayon"],
};
return compounds[mat] || [mat];
}

export async function POST(req: Request) {
try {
if (!process.env.LAMATIC_API_KEY) {
return Response.json(
{ materials: [], note: "Missing API key." },
{ status: 500 }
);
}

const { url } = await req.json();
Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated

// -------- PRIMARY AI CALL --------
const response = await fetch(
"https://yashasvisorganization952-yashasvisproject443.lamatic.dev/graphql",
{
method: "POST",
headers: {
Authorization: `Bearer ${process.env.LAMATIC_API_KEY}`,
"Content-Type": "application/json",
"x-project-id": "f16d4f23-0c7a-42df-b553-b41b1f166670",
Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated
},
body: JSON.stringify({
query: `query ExecuteWorkflow($workflowId: String!, $question: String, $url: String) {
executeWorkflow(workflowId: $workflowId payload: { question: $question url: $url }) {
status result
}
}`,
variables: {
workflowId: "55a58aab-872b-463f-94b1-e0fbfc1c2056",
question: "extract materials",
url,
},
}),
}
);
Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated

if (!response.ok) {
throw new Error("Primary API request failed");
}

const data = await response.json();
const workflowResult = data?.data?.executeWorkflow?.result;

let raw =
workflowResult?.answer ??
workflowResult?.output ??
workflowResult;

if (!raw) {
return Response.json({
materials: [],
note: "No response from AI",
});
}

const parsed = safeJSONParse(raw);

if (!parsed) {
return Response.json({
materials: [],
note: "Failed to parse AI response",
});
}

const rawMaterials: string[] =
parsed.materials ||
parsed.fabric ||
parsed.textiles ||
[];

Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated
if (rawMaterials.length === 0) {
return Response.json({
materials: [],
note:
parsed.note ||
"This manufacturer has not disclosed materials.",
});
}

// -------- NORMALIZATION --------
const normalized = rawMaterials.map(normalizeMaterial);
const displayMaterials = [
...new Set(normalized.flatMap(splitCompound)),
];

const known = displayMaterials.filter((m) => materialDB[m]);
const unknown = displayMaterials.filter((m) => !materialDB[m]);

let ecoScore = 0;
let skinScore = 0;
let ecoReasons: string[] = [];
let skinReasons: string[] = [];
let negatives: string[] = [];

// -------- KNOWN MATERIAL SCORING --------
known.forEach((mat) => {
const m = materialDB[mat];
if (!m) return;

if (m.biodegradable) {
ecoScore += 30;
ecoReasons.push(`${mat} is biodegradable`);
} else {
negatives.push(`${mat} is not biodegradable`);
}

if (m.waterUsage === "low") ecoScore += 10;
else if (m.waterUsage === "high")
negatives.push(`${mat} uses high water`);

if (m.chemicalUse === "low") ecoScore += 10;
else if (m.chemicalUse === "high")
negatives.push(`${mat} uses heavy chemicals`);

if (m.breathability === "high") {
skinScore += 30;
skinReasons.push(`${mat} is breathable`);
}

if (m.irritationRisk === "low") {
skinScore += 30;
skinReasons.push(`${mat} is skin-safe`);
} else if (m.irritationRisk === "high") {
negatives.push(`${mat} may irritate skin`);
}
});

// -------- AI FALLBACK FOR UNKNOWN --------
if (unknown.length > 0) {
try {
const aiRes = await fetch(
"https://yashasvisorganization952-yashasvisproject443.lamatic.dev/graphql",
{
method: "POST",
headers: {
Authorization: `Bearer ${process.env.LAMATIC_API_KEY}`,
"Content-Type": "application/json",
"x-project-id": "f16d4f23-0c7a-42df-b553-b41b1f166670",
},
body: JSON.stringify({
query: `query ExecuteWorkflow($workflowId: String!, $question: String) {
executeWorkflow(workflowId: $workflowId payload: { question: $question }) {
status result
}
}`,
variables: {
workflowId:
"55a58aab-872b-463f-94b1-e0fbfc1c2056",
question: `Analyze these materials: ${unknown.join(
", "
)}. Return JSON only.`,
},
Comment thread
coderabbitai[bot] marked this conversation as resolved.
Outdated
}),
}
);
Comment thread
coderabbitai[bot] marked this conversation as resolved.

if (aiRes.ok) {
const aiData = await aiRes.json();
let aiRaw =
aiData?.data?.executeWorkflow?.result?.answer;

const parsedAI = safeJSONParse(aiRaw);

if (parsedAI) {
ecoScore += parsedAI.ecoScore || 0;
skinScore += parsedAI.skinScore || 0;
ecoReasons.push(...(parsedAI.ecoReasons || []));
skinReasons.push(...(parsedAI.skinReasons || []));
negatives.push(...(parsedAI.negatives || []));
}
Comment thread
coderabbitai[bot] marked this conversation as resolved.
}
} catch (err) {
console.error("AI fallback failed:", err);
}
}

// -------- FINAL NORMALIZATION --------
ecoScore = Math.min(100, ecoScore);
skinScore = Math.min(100, skinScore);

return Response.json({
materials: displayMaterials,
ecoScore,
skinScore,
ecoReasons,
skinReasons,
negatives,
});
} catch (err) {
console.error("API ERROR:", err);
return Response.json(
{ materials: [], note: "Internal server error" },
{ status: 500 }
);
}
}
26 changes: 26 additions & 0 deletions kits/fablens/apps/app/globals.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
@import "tailwindcss";

:root {
--background: #ffffff;
--foreground: #171717;
}

@theme inline {
--color-background: var(--background);
--color-foreground: var(--foreground);
--font-sans: var(--font-geist-sans);
--font-mono: var(--font-geist-mono);
}

@media (prefers-color-scheme: dark) {
:root {
--background: #0a0a0a;
--foreground: #ededed;
}
}

body {
background: var(--background);
color: var(--foreground);
font-family: Arial, Helvetica, sans-serif;
}
Loading
Loading