# Конвертер Python ↔ Jupyter Notebook

Этот инструмент автоматически конвертирует Python файлы в Jupyter ноутбуки и наоборот.

## ✨ Основные возможности

- 🔄 **Двунаправленная конвертация**: py ↔ ipynb
- 📝 **Поддержка markdown**: автоматическое распознавание комментариев как markdown ячеек
- 📊 **Структурирование кода**: функции и классы в отдельных ячейках (включая декораторы)
- 🔗 **Многофайловое слияние**: объединение нескольких файлов в один
- 🌟 **Glob-шаблоны**: поддержка `*` и `?` для обработки множественных файлов
- ⚡ **Взаимообратимость**: конвертация туда-обратно сохраняет исходную структуру

## Логика конвертации

### Python → Jupyter (.py → .ipynb)

1. **Заголовочные комментарии** `""" # заголовок # """` становятся **markdown ячейками заголовков**
2. **Многострочные комментарии** `r"""..."""` и `"""..."""` становятся **markdown ячейками**
3. **Функции** и **классы** становятся **отдельными code ячейками**  
4. **Остальной код** группируется в **code ячейки**
5. **Docstring'и внутри функций/классов** остаются частью кода
6. **Обычные Python комментарии** `# текст` остаются обычными комментариями

### Jupyter → Python (.ipynb → .py)

1. **Markdown ячейки заголовки** `# заголовок #` → **заголовочные комментарии** `""" # заголовок # """`
2. **Markdown ячейки с `\` символами** → **комментарии с префиксом** `r"""..."""`
3. **Обычные markdown ячейки** → **многострочные комментарии** `"""..."""`
4. **Code ячейки** остаются как **обычный Python код**
5. Каждая ячейка отделяется **пустой строкой**
6. **Outputs** игнорируются


## 🚀 Использование

### Справка

```bash
# Подробная справка с примерами
py2jupyter --help
py2jupyter -h

# Краткая справка
py2jupyter
```

### Базовая конвертация

```bash
# Python → Jupyter (автоматическое имя выходного файла)
py2jupyter script.py

# Python → Jupyter (указанное имя)
py2jupyter script.py notebook.ipynb

# Python → Jupyter (автоматическое расширение)
py2jupyter script.py output  # → создаст output.ipynb

# Jupyter → Python (автоматическое имя)
py2jupyter notebook.ipynb

# Jupyter → Python (автоматическое расширение)
py2jupyter notebook.ipynb output  # → создаст output.py
```

### Многофайловое слияние

```bash
# Объединение нескольких Python файлов в один Notebook
py2jupyter script1.py script2.py script3.py combined.ipynb

# Объединение нескольких Notebook в один Python файл
py2jupyter notebook1.ipynb notebook2.ipynb merged.py
```

> **Примечания**:
> - При многофайловом слиянии выходной файл обязательно должен быть указан
> - Если расширение выходного файла не указано, оно определяется автоматически (.py → .ipynb, .ipynb → .py)

### Использование glob-шаблонов

```bash
# Конвертация всех Python файлов в текущей директории
py2jupyter *.py

# Конвертация файлов с определенным префиксом
py2jupyter test_*.py

# Конвертация с объединением в один файл
py2jupyter script_*.py combined.ipynb

# Поддержка различных шаблонов
py2jupyter data/test_?.py results.ipynb
```

> **Примечания**:
> - Шаблоны `*` и `?` автоматически расширяются в список файлов
> - Файлы сортируются по имени для предсказуемого порядка
> - При использовании шаблонов с одним файлом выходное имя генерируется автоматически



## 📋 Правила оформления

Для правильной конвертации Python файлов в Jupyter ноутбуки следуйте правилам оформления, описанным в файле [`PY_FORMAT_RULES.md`](PY_FORMAT_RULES.md) или скажите своей LLM следовать им.

Гарантируется, что для файлов, оформленных согласно правилам оформления, конвертация будет обратимой, то есть конвертация туда-обратно не будет менять код.

## 📋 Примеры

### Входной Python файл:
```python
""" # Моделирование физической системы # """

"""
Этот скрипт демонстрирует расчет энергии.
Формула: $E = \frac{1}{2}mv^2 + \frac{1}{2}kx^2$
"""

#> !pip install matplotlib
#> %matplotlib inline

import numpy as np
import matplotlib.pyplot as plt

def calculate_energy(x, v, m=1.0, k=100.0):
    """Расчет полной энергии системы (это docstring)"""
    kinetic = 0.5 * m * v**2
    potential = 0.5 * k * x**2
    return kinetic + potential

r"""
Раздел с анализом (содержит \ символы).
Интеграл: $\int_0^1 x^2 dx = \frac{1}{3}$
"""

""" # Параметры системы # """

# Обычный Python комментарий остается как есть
x0 = 0.1  # начальное смещение
v0 = 0.0  # начальная скорость
```

### Результат конвертации в Jupyter:
- **Cell 0** (markdown): `# Моделирование физической системы #`
- **Cell 1** (markdown): Описание с LaTeX формулой
- **Cell 2** (code): `import numpy as np` и `import matplotlib.pyplot as plt`
- **Cell 3** (code): `%matplotlib inline`
- **Cell 4** (code): `! pip install seaborn`
- **Cell 5** (code): Функция `calculate_energy` с docstring
- **Cell 6** (markdown): Раздел с анализом и интегралом
- **Cell 7** (markdown): `# Параметры системы #`
- **Cell 8** (code): Комментарии и инициализация переменных

### Результат обратной конвертации:
```python
""" # Моделирование физической системы # """

"""
Этот скрипт демонстрирует расчет энергии.
Формула: $E = \frac{1}{2}mv^2 + \frac{1}{2}kx^2$
"""

# ... код функций ...

#%matplotlib inline

#!pip install seaborn

r"""
Раздел с анализом (содержит \ символы).
Интеграл: $\int_0^1 x^2 dx = \frac{1}{3}$
"""

""" # Параметры системы # """
```

> **Умное определение префиксов**: ячейки с `\` символами получают префикс `r`, остальные - нет

## ⚙️ Технические особенности

- ✅ **UTF-8 кодировка**: полная поддержка Unicode
- ✅ **Сохранение структуры**: функции и классы остаются читаемыми  
- ✅ **Умное распознавание**: автоматическое определение типов ячеек
- ✅ **Масштабируемость**: работа с большими файлами (1000+ строк)
- ✅ **Взаимообратимость**: минимальные изменения при полном цикле конвертации
- ✅ **Совместимость**: поддержка Python 3.7+, адаптация под новые версии AST
- ✅ **Автоматические расширения**: умное определение .py/.ipynb при отсутствии расширения
- ✅ **Заголовочные комментарии**: специальный формат `""" # заголовок # """` для четких заголовков
- ✅ **Умные префиксы**: автоматическое определение `r` на основе наличия `\` символов
- ✅ **Универсальные комментарии**: поддержка как `r"""..."""`, так и обычных `"""..."""`
- ✅ **Очистка пустых строк**: автоматическое удаление пустых строк в начале и конце code ячеек
- ✅ **Разделение по пустым строкам**: автоматическое разделение больших блоков кода на меньшие ячейки при наличии двух и более пустых строк подряд (только на уровне нулевого отступа)
- ✅ **Поддержка magic команд**: автоматическая конвертация между `#%command` в .py и magic ячейками в .ipynb
- ✅ **Поддержка shell команд**: автоматическая конвертация между `#!command` в .py и shell ячейками в .ipynb
- ✅ **Встроенная справка**: подробная документация через `--help` с примерами и форматами

## 🔧 Требования

- Python 3.7+
- Стандартные библиотеки: `ast`, `json`, `pathlib` 


