Metadata-Version: 2.5
Name: mainframe-migration-toolkit
Version: 0.5.1
Summary: Runtime and deterministic tools for COBOL/JCL to PySpark migrations
Author: Mainframe Migration Toolkit
Requires-Python: >=3.10
Provides-Extra: all
Requires-Dist: pyarrow>=15; extra == 'all'
Requires-Dist: pyspark<5,>=3.5; extra == 'all'
Provides-Extra: aws
Requires-Dist: boto3<2,>=1.34; extra == 'aws'
Provides-Extra: dev
Requires-Dist: pytest-cov>=5; extra == 'dev'
Requires-Dist: pytest>=8.2; extra == 'dev'
Provides-Extra: parquet
Requires-Dist: pyarrow>=15; extra == 'parquet'
Provides-Extra: spark
Requires-Dist: pyspark<5,>=3.5; extra == 'spark'
Description-Content-Type: text/markdown

# Mainframe Migration Toolkit

Migre uma rotina JCL e seus programas COBOL para PySpark com o Devin: implementação incremental, testes e comparação da saída com o golden dataset.

Este guia usa o **[Devin CLI](https://docs.devin.ai/cli)** no mesmo ambiente dos arquivos. Tenha Python 3.10+, JDK 21 com `JAVA_HOME` configurado e Git. Os comandos são Bash; no Windows, use Git Bash com Python nativo do Windows.

## 1. Organize os arquivos

Exemplo: `JOBFAT.jcl` executa `PGM001`, `PGM002` e `PGM003`. A raiz `meu-job/` não precisa ser versionada:

```text
meu-job/
├── golden_dataset/
│   └── final.csv                    # saída esperada
├── input/                           # entradas fornecidas
├── output/                          # exportações físicas opcionais
├── external_programs/
│   └── programs.json                # especificações dos programas externos
├── spec/                            # especificações do AWS Transform
│   ├── jcl/
│   │   └── JOBFAT-jcl.json
│   └── cobol/                       # PGM001-cbl.json, PGM002-cbl.json, PGM003-cbl.json
└── codebase/                        # fontes originais
    ├── jcl/
    │   └── JOBFAT.jcl
    ├── copybook/
    └── cobol/                       # PGM001.cbl, PGM002.cbl, PGM003.cbl
```

O JSON de externos deve mapear nomes para descrições, por exemplo: `{"CALCTAX": "Calcula o imposto conforme a especificação..."}`. Use `{}` quando não houver programas externos.

## 2. Instale o toolkit

No terminal, dentro da raiz do exemplo:

```bash
cd /caminho/para/meu-job
python -m venv .venv
# Git Bash + Python nativo do Windows:
source .venv/Scripts/activate
# Em Linux/macOS, use: source .venv/bin/activate
python -m pip install --upgrade "mainframe-migration-toolkit[all,dev]"
export PYSPARK_PYTHON="$(python -c 'import sys; print(sys.executable)')"
export PYSPARK_DRIVER_PYTHON="$PYSPARK_PYTHON"
```

Isso instala o toolkit, PySpark, suporte a Parquet e ferramentas de teste. O ambiente Python fica fora do repositório da migração.

## 3. Inicialize o workspace

Ainda em `meu-job/`:

```bash
python -m mainframe_toolkit init-workspace .
```

O comando cria `migration/`, inicializa seu Git e instala as instruções, a skill e os agentes nativos Devin. Os arquivos fornecidos permanecem na raiz, fora desse Git. Não é necessário configurar ACP.

Diretórios existentes com underscore são reconhecidos; não é necessário criar links. Os nomes com hífen também são aceitos e têm precedência se ambos existirem. Os caminhos escolhidos ficam em `migration/mainframe-migration.json`.

Confira o resultado: `git_initialized` deve ser `true` e `skipped_conflicts` deve estar vazio. Se houver conflitos, resolva os arquivos indicados antes de iniciar; evite sobrescrever customizações com `--force`.

## 4. Abra o Devin e peça a migração

No mesmo terminal, com a `.venv` ativa, inicie uma nova sessão **dentro de `migration/`**:

```bash
cd migration
devin
```

Envie este pedido, ajustando o nome do job e do golden:

```text
Use a skill migrate-mainframe-job para migrar a rotina JOBFAT.

JCL: ../codebase/jcl/JOBFAT.jcl
Especificações: ../spec/jcl/JOBFAT-jcl.json e ../spec/cobol/
Entradas: ../input/
Programas externos: ../external_programs/programs.json
Saída esperada: ../golden_dataset/final.csv

Desenvolvimento local: Git Bash com Python nativo do Windows, sem winutils.
Use --io-backend local nas execuções e passe context.io_backend aos
readers/writers dos adapters e sinks; mantenha os programas puros.

Execute o preflight e converta todos os programas na ordem real do JCL.
Teste e execute o prefixo após cada programa. Continue até a rotina
completa produzir 100% de igualdade célula a célula com o golden.

Mantenha o handoff entre programas em memória. Autorizo ../output/
como destino apenas das saídas físicas exigidas pela especificação.
Preserve as fontes e os dados fornecidos.
```

Também é possível chamar a skill por [`/migrate-mainframe-job`](https://docs.devin.ai/cli/extensibility/skills/overview). O agente conduz a preparação, implementação, recuperação de dependências e validação; você não precisa chamar cada agente manualmente.

## Executar localmente

Após a geração, dentro de `migration/`, usando o nome real do módulo gerado:

```bash
python -m converted.jobfat_job --io-backend local
```

O backend local lê/grava CSV com Python e Parquet com PyArrow, incluindo auditorias, sem usar os readers/writers de arquivos do Hadoop. As saídas são diretórios com arquivos `part-*`. PySpark e Java continuam executando as transformações; dados entre programas continuam em memória.

Use dados de teste que caibam no driver: entradas são carregadas em memória; saídas usam `toLocalIterator`, com memória proporcional à maior partição e lotes Parquet de 4.096 linhas. Esse modo não reproduz S3, permissões ou escrita distribuída. Na AWS, use `--io-backend spark` (padrão), mantendo o mesmo código de negócio. Readers e writers customizados continuam podendo ser fornecidos como funções.

Os testes do backend local foram executados em macOS; a execução completa em Windows nativo ainda precisa ser confirmada nesse ambiente. O toolkit não instala `winutils`.

## Executar no Glue

Localize `glue/entrypoint.py` com `python -m mainframe_toolkit references --path`. Adapte o import de `build_steps` para sua rotina e a opção de exportação. A referência usa a sessão do Glue, lê parâmetros e chama os mesmos programas puros.

Disponibilize o pacote `converted/` em um ZIP e o wheel do toolkit no S3. Configure `--extra-py-files` com o ZIP e `--additional-python-modules` com o wheel, sem os extras `[all,dev]`: o Glue fornece Spark e Boto3. Configure também estes parâmetros do exemplo:

```text
--input_uri       s3://meu-bucket/input
--output_uri      s3://meu-bucket/output
--audit_uri       s3://meu-bucket/audit
--processing_date 2026-01-31
```

O runtime grava datasets pelo Spark e o manifesto pelo Boto3, usando a role do job. Nos adapters, use `join_location(context.input_dir, "arquivo.csv")` e o equivalente para saídas; não converta URIs em `Path`. O writer de artefatos pode ser substituído por `PipelineContext(..., artifact_writer=meu_writer)`.

Versão do Glue, permissões, workers e validação da rotina na AWS ficam a cargo do usuário. A referência não habilita bookmarks ou retomada automática. Para usar o writer S3 fora do Glue, instale o extra `[aws]`. Consulte a [configuração de dependências do Glue](https://docs.aws.amazon.com/glue/latest/dg/aws-glue-programming-python-libraries.html).

## Onde encontrar a entrega

- `migration/converted/`: código Python, testes e entrypoint da rotina.
- `migration/audit/`: auditorias por programa e manifesto da execução.
- `migration/synthetic/`: recursos reconstruídos somente quando necessários.
- `migration/RELATORIO_FINAL.md`: resultado da comparação e comandos para executar a rotina, após o aceite.
- `output/`: somente as exportações físicas solicitadas; criar a pasta não habilita gravações automaticamente.

Para usar Claude Code, execute `claude --agent mainframe-migration-supervisor` dentro de `migration/`.
