/ Модель

Характеристики

Контекст
40 960 токенов
Параметры
3,7 млрд
Лицензия
Apache 2.0
Архитектура
qwen3 · dense
Базовая модель
Qwen3-4B
Библиотека
transformers
Опубликована
7 июн 2026

Cassini-1.0

Генерация текстаТекст → текст6 профессий

Cassini-1.0 извлекает из кода Python, JavaScript и TypeScript структурированные сведения для статического анализа и графов зависимостей.

29скачиваний за 30 дней22лайкавеса обновлены7 июн 2026

Бенчмарки

Как модель справилась с задачами пользователей ailist и что о ней публикуют открытые лидерборды

Тесты пользователейпока нет

Никто ещё не опубликовал тест этой модели. Соберите бенчмарк из своих задач — результат появится здесь.

  1. Добавьте модель в бенчмарк

    Вместе с другими моделями категории «Текст» — сравнение идёт внутри одной категории.

  2. Опишите свои задачи

    Напишите запросы, при необходимости приложите файлы и эталонные ответы.

  3. Запустите и опубликуйте

    Модели ответят на каждую задачу, судья оценит ответы. Опубликованный результат появится на этой странице.

Публичные оценки

Из открытых лидербордов. Сравнивайте результаты одного теста при одинаковых условиях — отсутствие оценки не значит, что модель хуже.

В подключённых источниках результатов для этой модели пока нет.

Что умеет модель

Описание составлено по карточке модели и метаданным Hugging Face

Cassini-1.0 — дообученная модель семейства Qwen3, разработанная LatentForce-ai для извлечения структурированных сведений из исходного кода. Она принимает файлы Python, JavaScript и TypeScript и за один проход формирует JSON с импортами, определениями, ссылками, вызовами, назначениями типов и дополнительными данными об определениях.

Модель предназначена для инженерных конвейеров статического анализа: построения графов зависимостей и вызовов, индексации символов и анализа влияния изменений в крупных репозиториях. В карточке заявлен результат 77,6% F1 на оценке извлечения при общей стоимости инференса $0,17; это заявление разработчика, а подробности методики оценки в предоставленном фрагменте не раскрыты. Модель основана на Qwen/Qwen3-4B, содержит около 3,7 млрд параметров, имеет контекст 40 960 токенов и рассчитана на запуск через vLLM. Лицензия — Apache-2.0.

Сценарии применения

  • извлечение импортов и внутренних зависимостей из файлов Python
  • построение графа вызовов функций и методов
  • индексация классов, функций и констант в репозитории
  • поиск ссылок на модули и их атрибуты в коде
  • извлечение назначений типов для анализа кода
  • подготовка структурированных данных для анализа влияния изменений

Ограничения

Поддерживаемые языки кода в карточке ограничены Python, JavaScript и TypeScript; заявленный результат F1 приведён без подробностей методики оценки в доступном фрагменте README.

Для каких профессий подходит6

Разделы каталога профессий, в задачах которых используется эта модель

Все профессии

Также подходит для

Карточка модели

README от автора на Hugging Face, как он его опубликовал

Открыть на Hugging Face

Cassini is a series of small language models fine-tuned for static code feature extraction. Given a source file, it produces the structured symbolic metadata that powers dependency resolution, call graph construction, and type inference at scale.

Model Highlights

  • Fine-tuned on Python, JavaScript, and TypeScript for structured code feature extraction
  • Purpose-built for extraction. Trained to read code the way a static analyzer does, symbolically and structurally. Outputs valid JSON consumed directly by downstream dependency resolvers and call graph engines
  • Extracts six symbolic fields per source file — imports, definitions, references, calls, type assignments, and rich definition metadata — in a single inference pass
  • Built for engineering teams who need structured code intelligence at scale. Dependency analysis across large or monorepo codebases, call graph and impact analysis pipelines, and tooling that requires symbolic metadata without the overhead of a full compiler or language server
  • State-of-the-art cost efficiency for structured code extraction — Cassini-1.0 achieves 77.6% F1 matching or exceeding general-purpose models that cost 17–43× more: Qwen3.7-Max ($3.03, 77.6%), Gemini 3.5 Flash ($5.84, 74.2%), and Gemini 3.1 Pro ($7.57, 72.5%) — all at a total inference cost of $0.17

cost_vs_f1_150

What Cassini Extracts

FieldIn plain termsExampleUsed for
importsEvery internal dependency a file pulls in — what is imported, from where, and under what aliasfrom .utils import helper as hBuilding the file-to-file dependency graph
definitionsEvery class, function, and constant defined at the top level of the fileclass UserService, def get_user, MAX_RETRIESPopulating the project-wide symbol index
referencesWhen a whole module is imported and its attributes are accessed later in codeimport pkg then pkg.connect() → records connect on pkgResolving module-level attribute call sites
callsEvery function or method invocation — who is calling, what is being called, how it is called, and on what receiverself.cache.get(key) inside UserService.fetchConstructing the call graph, one edge per invocation
type_assignmentsEvery variable binding where the type can be inferred, including factory calls where only the function name is knownself.db = Database() or result = build_result()Inferring receiver types so method calls resolve to the right class
definitions_richExtended metadata per definition — kind, parent class, base classes, parameters, return type, and line numbercreate is a method on UserService, returns User, takes data: dictInheritance resolution, super() walking, and return-type back-filling for factory functions

Technical Specifications

ParameterValue
FrameworkUnsloth + TRL SFTTrainer
Training methodSupervised Finetuning using LoRA
Base modelQwen/Qwen3-4B
Precisionbf16
Max sequence length20,480 tokens
Epochs5
Per-device batch size16
Gradient accumulation steps2
Effective batch size32
Learning rate8e-4
LR schedulerCosine
Warmup steps10
Weight decay0.01
OptimizerAdamW 8-bit
LoRA rank (r)1
LoRA alpha2
LoRA dropout0
LoRA target modulesq_proj, k_proj, v_proj, o_proj, gate_proj, up_proj, down_proj
HardwareNVIDIA RTX Pro 9000 (96 GB VRAM)

Usage

Cassini-1.0 is served via vLLM and queried through its OpenAI-compatible endpoint. The model takes a source file as input and returns a structured JSON object containing six symbolic extraction fields.


Prerequisites

1. Install dependencies

pip install vllm openai pyyaml

2. Download the prompt template

The extraction prompt is shipped as python.yaml and javascript.yaml (for both JS and TS) in this repository. Clone or download it before running inference:

# Clone the full repo
git clone https://huggingface.co/LatentForce-ai/Cassini-1.0

# Or download the prompt file only
wget https://huggingface.co/LatentForce-ai/Cassini-1.0/resolve/main/prompts/javascript.yaml

3. Start the vLLM server

In a separate terminal, serve the model:

vllm serve LatentForce-ai/Cassini-1.0 --max-model-len 20480

The server will be available at http://127.0.0.1:8000 by default. Allow 1–2 minutes for the model to load before sending requests.


Minimal Inference

The following snippet runs inference on a single source file and prints the extracted JSON. Point SOURCE_FILE at any .py file, and run.

import json
import yaml
from openai import OpenAI

# ---------------------------------------------------------------------------
# Config
# ---------------------------------------------------------------------------

VLLM_URL    = "http://127.0.0.1:8000/v1"
MODEL_ID    = "LatentForce-ai/Cassini-1.0"
PROMPT_YAML = "python.yaml"           # path to the prompt template from this repo
SOURCE_FILE = "main.py"  # path to the source file to analyze
MAX_TOKENS  = 6144

# ---------------------------------------------------------------------------
# Load prompt template
# ---------------------------------------------------------------------------

with open(PROMPT_YAML) as f:
    config = yaml.safe_load(f)

prompt_template = config["prompt"]

# ---------------------------------------------------------------------------
# Prepare prompt
# ---------------------------------------------------------------------------

with open(SOURCE_FILE) as f:
    source_code = f.read()

prompt = (
    prompt_template
    .replace("FILEPATH_PLACEHOLDER", SOURCE_FILE)
    .replace("CONTENT_PLACEHOLDER", source_code)
)

# ---------------------------------------------------------------------------
# Run inference
# ---------------------------------------------------------------------------

client = OpenAI(base_url=VLLM_URL, api_key="no-key")

response = client.chat.completions.create(
    model=MODEL_ID,
    messages=[{"role": "user", "content": prompt}],
    temperature=0,
    max_tokens=MAX_TOKENS,
    extra_body={"chat_template_kwargs": {"enable_thinking": False}},
)

# ---------------------------------------------------------------------------
# Parse output
# ---------------------------------------------------------------------------

raw = response.choices[0].message.content


def parse_json_response(text: str) -> dict | None:
    """Strip markdown fences if present and parse JSON."""
    text = text.strip()
    if text.startswith("```"):
        first_newline = text.find("\n")
        if first_newline != -1:
            inner = text[first_newline + 1:]
            close = inner.rfind("```")
            if close != -1:
                inner = inner[:close]
            text = inner.strip()
    try:
        return json.loads(text)
    except json.JSONDecodeError:
        pass
    # Fallback: find first complete JSON object
    start, end = text.find("{"), text.rfind("}")
    if start != -1 and end != -1 and end > start:
        try:
            return json.loads(text[start:end + 1])
        except json.JSONDecodeError:
            pass
    return None


result = parse_json_response(raw)

if result is None:
    print("Warning: model output could not be parsed as JSON.")
    print("Raw output:", raw)
else:
    print(json.dumps(result, indent=2))

Example Output

Suppose for a small Python file given below

"""
Declare and configure the signals for the impress core application
"""

from functools import partial

from django.core.cache import cache
from django.db import transaction
from django.db.models import signals
from django.dispatch import receiver

from core import models
from core.tasks.search import trigger_batch_document_indexer
from core.utils.users import get_users_sharing_documents_with_cache_key


@receiver(signals.post_save, sender=models.Document)
def document_post_save(sender, instance, **kwargs):  # pylint: disable=unused-argument
    """
    Asynchronous call to the document indexer at the end of the transaction.
    Note : Within the transaction we can have an empty content and a serialization
    error.
    """
    transaction.on_commit(partial(trigger_batch_document_indexer, instance))


@receiver(signals.post_save, sender=models.DocumentAccess)
def document_access_post_save(sender, instance, created, **kwargs):  # pylint: disable=unused-argument
    """
    Asynchronous call to the document indexer at the end of the transaction.
    Clear cache for the affected user.
    """
    if not created:
        transaction.on_commit(
            partial(trigger_batch_document_indexer, instance.document)
        )

    # Invalidate cache for the user
    if instance.user:
        cache_key = get_users_sharing_documents_with_cache_key(instance.user)
        cache.delete(cache_key)


@receiver(signals.post_delete, sender=models.DocumentAccess)
def document_access_post_delete(sender, instance, **kwargs):  # pylint: disable=unused-argument
    """
    Clear cache for the affected user when document access is deleted.
    """
    if instance.user:
        cache_key = get_users_sharing_documents_with_cache_key(instance.user)
        cache.delete(cache_key)

Cassini-1.0 produces the following structured JSON

{
  "imports": [
    {
      "module": "core",
      "names": [
        "models"
      ],
      "alias": {}
    },
    {
      "module": "core.tasks.search",
      "names": [
        "trigger_batch_document_indexer"
      ],
      "alias": {}
    },
    {
      "module": "core.utils.users",
      "names": [
        "get_users_sharing_documents_with_cache_key"
      ],
      "alias": {}
    }
  ],
  "references": [],
  "calls": [
    {
      "caller": "__module__",
      "callee_text": "receiver",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 14
    },
    {
      "caller": "document_post_save",
      "callee_text": "on_commit",
      "kind": "method",
      "receiver": "transaction",
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 21
    },
    {
      "caller": "document_post_save",
      "callee_text": "partial",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 21
    },
    {
      "caller": "document_post_save",
      "callee_text": "trigger_batch_document_indexer",
      "kind": "hook",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "core/tasks/search.py",
      "line": 21
    },
    {
      "caller": "__module__",
      "callee_text": "receiver",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 24
    },
    {
      "caller": "document_access_post_save",
      "callee_text": "on_commit",
      "kind": "method",
      "receiver": "transaction",
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 31
    },
    {
      "caller": "document_access_post_save",
      "callee_text": "partial",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 32
    },
    {
      "caller": "document_access_post_save",
      "callee_text": "trigger_batch_document_indexer",
      "kind": "hook",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "core/tasks/search.py",
      "line": 32
    },
    {
      "caller": "document_access_post_save",
      "callee_text": "get_users_sharing_documents_with_cache_key",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "core/utils/users.py",
      "line": 37
    },
    {
      "caller": "document_access_post_save",
      "callee_text": "delete",
      "kind": "method",
      "receiver": "cache",
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 38
    },
    {
      "caller": "__module__",
      "callee_text": "receiver",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 41
    },
    {
      "caller": "document_access_post_delete",
      "callee_text": "get_users_sharing_documents_with_cache_key",
      "kind": "free",
      "receiver": null,
      "receiver_type_hint": null,
      "callee_file_hint": "core/utils/users.py",
      "line": 47
    },
    {
      "caller": "document_access_post_delete",
      "callee_text": "delete",
      "kind": "method",
      "receiver": "cache",
      "receiver_type_hint": null,
      "callee_file_hint": "external",
      "line": 48
    }
  ],
  "type_assignments": [
    {
      "scope": "document_access_post_save",
      "var": "cache_key",
      "type": null,
      "type_module": null,
      "from_call": "get_users_sharing_documents_with_cache_key"
    },
    {
      "scope": "document_access_post_delete",
      "var": "cache_key",
      "type": null,
      "type_module": null,
      "from_call": "get_users_sharing_documents_with_cache_key"
    }
  ],
  "definitions": [
    "document_post_save",
    "document_access_post_save",
    "document_access_post_delete"
  ],
  "definitions_rich": [
    {
      "name": "document_post_save",
      "kind": "function",
      "parent": null,
      "bases": [],
      "params": [
        {
          "name": "sender",
          "type": null
        },
        {
          "name": "instance",
          "type": null
        }
      ],
      "returns": null,
      "line": 15
    },
    {
      "name": "document_access_post_save",
      "kind": "function",
      "parent": null,
      "bases": [],
      "params": [
        {
          "name": "sender",
          "type": null
        },
        {
          "name": "instance",
          "type": null
        },
        {
          "name": "created",
          "type": null
        }
      ],
      "returns": null,
      "line": 25
    },
    {
      "name": "document_access_post_delete",
      "kind": "function",
      "parent": null,
      "bases": [],
      "params": [
        {
          "name": "sender",
          "type": null
        },
        {
          "name": "instance",
          "type": null
        }
      ],
      "returns": null,
      "line": 42
    }
  ]
}

Как запустить

На своей GPU в ailist. Цена — по текущим предложениям провайдеров

GPU в ailist

Универсальный рантайм · transformers

Можно запустить

Подбираем GPU…

Класс архитектуры
Qwen3ForCausalLM
Ревизия весов
7167fc1

0 моделей