Company and product entity extraction.
We will fine-tune a small LoRA adapter to read a short sentence and return only JSON containing two arrays: companies and products. The job is intentionally small so the first Tinker run tests the workflow, not model ambition.
What Tinker will do.
The Python script owns the data formatting and training loop. Tinker handles the remote GPU work behind the API.
python-dotenv loads TINKER_API_KEY from .env.ServiceClient creates a LoRA training client for Qwen/Qwen3-8B.forward_backward_async computes gradients, then optim_step_async updates weights.The output is fixed JSON.
The model should not explain its answer. It should return only the object below, with arrays even when there is one or zero entities.
Prompt shape
The prompt tells the model exactly what to extract and repeats the schema before the JSON: marker.
weights=0.Text:
"Microsoft and OpenAI expanded Copilot support for GPT-4o."
Return only JSON with this schema: {"companies":[],"products":[]}
JSON:
Completion shape
The completion is compact JSON. Product names keep their full names even when they include company words.
weights=1.Examples we train on.
The first run includes both single-company and multi-company sentences so the array behavior is explicit.
| Input Text | Companies | Products | Why It Matters |
|---|---|---|---|
| Apple announced new MacBook Pro models with M4 chips. | Apple | MacBook Pro, M4 | basicSimple one-company extraction. |
| Anthropic launched Claude Opus 4.1 through Amazon Bedrock. | Anthropic, Amazon | Claude Opus 4.1, Amazon Bedrock | multi-companyCompany appears inside product name too. |
| Nvidia partnered with Oracle to bring Blackwell GPUs to Oracle Cloud. | Nvidia, Oracle | Blackwell, Oracle Cloud | multi-companyPartnership sentence with cloud product. |
| Microsoft and OpenAI expanded Copilot support for GPT-4o. | Microsoft, OpenAI | Copilot, GPT-4o | coordinationTwo companies joined by “and”. |
How we decide if it worked.
This first test is about validating the Tinker loop and output contract. We should expect some extraction mistakes with such a tiny dataset.
Valid JSON
The output parses with json.loads and contains exactly companies and products.
Entity recall
Expected companies and products are present, including cases with more than one company.
No hallucinations
The model avoids adding entities that are not present in the sentence.
"Salesforce added Agentforce features to Slack."
expected: {"companies":["Salesforce"],"products":["Agentforce","Slack"]}
"Adobe Firefly is now integrated into Photoshop."
expected: {"companies":["Adobe"],"products":["Firefly","Photoshop"]}
"Perplexity launched Comet as an AI browser."
expected: {"companies":["Perplexity"],"products":["Comet"]}
Commands to run it.
The script lives at learning/tinker-thinking-machines/entity_extraction_sft.py.
uv pip install tinker python-dotenv
cp .env.example .env
# Edit .env:
TINKER_API_KEY=your-api-key-here
python learning/tinker-thinking-machines/entity_extraction_sft.py
# Optional knobs:
python learning/tinker-thinking-machines/entity_extraction_sft.py \
--epochs 5 \
--learning-rate 1e-4 \
--checkpoint-name entity-extraction-first-test