feat: descrição arquivística NOBRADE multinível com exportação EAD 3, EAC-CPF e AtoM

- pipeline/nobrade: normalizadores de datas (ISO 8601-2), séries, autoridades,
  espécie/suporte, direitos, lugar e assuntos; montagem dos níveis 0–5 com
  código de referência BR RJXYZ.BF.<seção>.<série>.<handle>.<imagem>
- validador dos elementos obrigatórios: 0 pendências em 26.454 unidades
- EAD 3 e 457 EAC-CPF validados contra os XSD
- mural: cartão com código, data normalizada, série e reprodução; filtro por série
This commit is contained in:
2026-09-30 21:22:00 +02:00
parent e92df83a78
commit 23b56e8c87
46 changed files with 19562 additions and 68 deletions
+7
View File
@@ -20,3 +20,10 @@ pipeline/rejeitados/
web/atlas/*.webp
pipeline/catalogo.jsonl
pipeline/wordpress-posts.jsonl
# descrição NOBRADE: saídas pesadas, regeneradas por `python -m nobrade` (vão para o bucket)
descricao/unidades.jsonl
descricao/ead/
descricao/eac/
descricao/atom.csv
__pycache__/
+64 -12
View File
@@ -8,6 +8,12 @@ Este arquivo resume a norma (seções 1–4) e registra as decisões de aplicaç
tomadas para a cópia digital da Brasiliana Fotográfica (seção 5). A
implementação está em `pipeline/nobrade/` e a saída em `descricao/`.
```bash
cd pipeline
python3 -m nobrade # descricao/: unidades, autoridades, revisão, pendências, EAD 3, EAC-CPF, AtoM
python3 -m nobrade.mural # leva código, data, série e suporte para web/atlas/atlas-map.json
```
---
## 1. O que é a NOBRADE
@@ -79,6 +85,11 @@ Em **negrito**, os 7 obrigatórios.
não expuser os níveis, o elemento 1.4 tem de listar os títulos de todos os
níveis superiores (1.1.4).
- Exemplos da norma: `BR MN`, `BR CPDOC JG`, `BR AN Q6.LEG.COR,TEL`.
- Na prática (código CODEARQ), o código da entidade leva a UF colada à sigla,
e as partes da unidade vão separadas por ponto. Exemplo do Arquivo Geral da
Cidade do Rio de Janeiro: `BR RJAGCRJ.SOP.NL.AVE.03.01` = país · UF+entidade ·
fundo (Secretaria de Obras Públicas) · série (Negrão de Lima) · subsérie
(Avenidas) · dossiê 03 · item 01, a imagem em si.
### 1.2 Título
- Registrar o título original. Na falta dele, atribuir um título formado a
@@ -155,18 +166,25 @@ de origem. Por isso:
| Nível | Unidade | Origem | Código |
|---|---|---|---|
| 0 | Acervo da entidade | — | `BR XYZ` |
| 1 | Coleção Brasiliana Fotográfica (cópia digital) | — | `BR XYZ BF` |
| 2 | Seção = instituição de origem | `community` | `BR XYZ BF.IMS` |
| 3 | Série = coleção/fundo de origem | `dc.source` normalizado | `BR XYZ BF.IMS.GF` |
| 4 | Dossiê = item do DSpace (handle) | `handle` | `BR XYZ BF.IMS.GF.12345` |
| 5 | Item documental = cada imagem do dossiê | bitstreams | `BR XYZ BF.IMS.GF.12345.2` |
| 0 | Acervo da entidade | — | `BR RJXYZ` |
| 1 | Coleção Brasiliana Fotográfica (cópia digital) | — | `BR RJXYZ.BF` |
| 2 | Seção = instituição de origem | `community` | `BR RJXYZ.BF.IMS` |
| 3 | Série = coleção/fundo de origem | `dc.source` normalizado | `BR RJXYZ.BF.IMS.GF` |
| 4 | Dossiê = item do DSpace (handle) | `handle` | `BR RJXYZ.BF.IMS.GF.12345` |
| 5 | Item documental = cada imagem do dossiê | ledger do bucket | `BR RJXYZ.BF.IMS.GF.12345.01` |
- `BR XYZ` é **provisório** até o CONARQ atribuir um código. A troca é uma
- `RJXYZ` é **provisório** até o CONARQ atribuir um código. A troca é uma
constante em `pipeline/nobrade/config.py`.
- **Toda imagem é um item de nível 5**, mesmo quando o dossiê tem só uma
(`.01`), como no AGCRJ. Os 115 dossiês com várias imagens têm `.01`–`.06`.
- O código do dossiê termina no número do handle (proc. 1.1.2.2), então
sobrevive a reclassificações de série sem perder a ligação com a origem.
- Itens sem série identificável ficam na série `AV` ("Avulsos") da sua seção.
Notações de caixa e de negativo em `dc.source` (`CX 14`, `NV 2056`) não viram
série: vão para 5.1 como notação na origem.
- O IHGB é a única instituição que publica o próprio código NOBRADE
(`BR RJIHGB 064IG 0278`, em `dc.identifier`). Ele fica em 5.1 como código na
origem.
### 5.3 De onde vem cada elemento
@@ -174,7 +192,7 @@ de origem. Por isso:
|---|---|---|
| 1.2 Título | `dc.title` | nome da coleção, instituição ou série |
| 1.3 Data | `dc.date` normalizado + ISO 8601. `dc.coverage` → data tópica | datas-limite dos filhos |
| 1.5 Dimensão | `dc.type` → espécie + suporte. Cópia digital: pixels e bytes | soma por espécie |
| 1.5 Dimensão | `dc.type` → espécie + suporte; cor e medidas que AN e AGCRJ põem em `dc.description`. Cópia digital: arquivos e bytes | soma por espécie |
| 2.1 Produtor | `dc.contributor` (fotógrafo), forma autorizada | colecionador / instituição |
| 2.3 Hist. arquivística | `dc.date.accessioned` (entrada no DSpace), data da coleta | relato da coleta (nível 1) |
| 2.4 Procedência | Brasiliana Fotográfica, handle, data da coleta | idem, agregado |
@@ -202,12 +220,46 @@ de origem. Por isso:
- `descricao/eac/`: um EAC-CPF por autoridade.
- `descricao/pendencias.md`: relatório do validador dos obrigatórios.
- `descricao/revisao/*.tsv`: tabelas dos normalizadores para revisão manual.
Uma correção feita ali prevalece na próxima geração.
- `pipeline/nobrade/ajustes/series.tsv` (colunas `instituicao`, `dc_source`,
`titulo`): correção manual de série, que prevalece sobre a regra na próxima
geração.
- `descricao/atom.csv`: importação no AtoM (modelo ISAD).
### 5.5 Pendências fora do código
Versionados no git: textos, revisão, autoridades e pendências. `unidades.jsonl`,
`ead/`, `eac/` e `atom.csv` são regenerados e vão para o bucket.
### 5.5 Decisões de normalização
- **Datas:** 190 padrões distintos na origem. Saem na forma da norma
(`[ca. 1905]`, `[193-?]`, `8/2/1890-18/4/1890`) e em ISO 8601-2/EDTF
(`1905~`, `193X?`, `1890-02-08/1890-04-18`). `circa` fica como `ca.`,
convenção do AACR2, que a norma cita. Os 167 carimbos de registro do DSpace
gravados em `dc.date` não são tratados como data de produção. Os dossiês sem
data recebem uma data atribuída (proc. 1.3.3.2), `[A-B?]`, a partir do
período de atividade do autor, ou senão das datas-limite da série, ou senão
das da instituição. A base da atribuição fica anotada.
- **Título ausente:** atribuído entre colchetes a partir da descrição ou dos
assuntos (proc. 1.2).
- **Espécie ausente:** presumida fotografia, com nota. O repositório inteiro é
fotográfico.
- **Autoridades:** grafias unidas por chave sem acento e por inversão ("Marc
Ferrez" → "Ferrez, Marc"). A forma autorizada é a variante com datas mais
completas; as outras viram remissivas (8.1.4). Anônimos não viram autoridade.
- **Assuntos:** as traduções inglesas que o DSpace da BN repete ficam separadas
(`assuntos_eng`). Os assuntos seguem o vocabulário da origem, sem controle
adicional.
- **Direitos:** quatro categorias: domínio público, uso cultural liberado,
requer autorização do detentor, e consultar o detentor. O texto da origem
fica em 6.2.
- **Valores corrompidos na origem** (fragmentos de XML ou hash no lugar do
texto): desconsiderados e anotados em 6.2.
### 5.6 Pendências fora do código
- [ ] Pedir ao CONARQ o código da entidade custodiadora (proc. 1.1.1) e
substituir `BR XYZ`.
substituir `RJXYZ`, além de definir o nome da entidade (`ENTIDADE_NOME`).
- [ ] Revisar `descricao/revisao/series.tsv` e `datas.tsv` (valores que o
normalizador não resolveu).
- [ ] Revisar os textos dos níveis 2 e 3 em `descricao/textos/`.
- [ ] Revisar os textos dos níveis 2 e 3 em `descricao/textos/`. Os das
seções são rascunhos.
- [ ] Revisar as 813 datas atribuídas pelo arquivista (`revisao/datas.tsv`).
File diff suppressed because one or more lines are too long
+29
View File
@@ -0,0 +1,29 @@
# Pendências da descrição NOBRADE
Gerado por `python -m nobrade`. Obrigatórios reprovam; avisos pedem revisão.
| Nível | Unidades |
|---|--:|
| 0 acervo | 1 |
| 1 coleção | 1 |
| 2 seção | 15 |
| 3 série | 115 |
| 4 dossiê | 13.060 |
| 5 item | 13.262 |
## Obrigatórios faltando: 0
Nenhum. Todas as unidades têm os elementos obrigatórios do seu nível.
## Avisos
| Aviso | Dossiês |
|---|--:|
| 4.2 condição de reprodução não informada na origem | 8.036 |
| 1.5 espécie presumida | 5.422 |
| 2.1 autoria não identificada | 3.287 |
| nível 3 em Avulsos — série de origem não identificada | 2.865 |
| 3.1 sem âmbito e conteúdo | 2.775 |
| 1.3 data atribuída pelo arquivista — conferir | 813 |
| valores corrompidos na origem | 105 |
| 6.1 preservação indisponível na origem | 69 |
+458
View File
@@ -0,0 +1,458 @@
id forma_autorizada tipo ocorrencias variantes
A0001 Ferrez, Marc, 1843-1923 pessoa 1960 Ferrez, Marc | Marc Ferrez | Marc Ferrez (Autoria)
A0002 Malta, Augusto, 1864-1957 pessoa 1175 Augusto Malta | MALTA, Augusto | Malta, Augusto | Malta, Augusto,1864-1957
A0003 Escola de Aviação Militar entidade coletiva 596 ""
A0004 Santos, Guilherme pessoa 420 ""
A0005 Gutierrez, Juan, 1859-1897 pessoa 373 Gutierrez, Juan | Gutierrez, Juan, m. 1897
A0006 Kfuri, Jorge, 1893-1965 pessoa 294 Kfuri, Jorge
A0007 Klumb, Revert Henrique, fl. 1855-1880 pessoa 290 Klumb, Revert Henrique
A0008 Leuzinger, Georges pessoa 257 ""
A0009 Escola de Aeronáutica entidade coletiva 174 ""
A0010 Officina de Paulo Robin entidade coletiva 169 ""
A0011 Robin, Paulo, m. 1897 pessoa 158 ""
A0012 Photographia Brazileira entidade coletiva 126 ""
A0013 Wischral, Arthur pessoa 124 ""
A0014 Gaensly, Guilherme, 1843-1928 pessoa 123 Gaensly, Guilherme
A0015 Escola de Aeronáutica Militar entidade coletiva 88 ""
A0016 Merrill, D. B. (Dana B.) pessoa 86 ""
A0017 Pacheco, Joaquim Insley, 1830-1912 pessoa 82 Pacheco, Joaquim Insley | Pacheco, Joaquim Insley, m. 1912
A0018 Azevedo, Militão Augusto de pessoa 75 ""
A0019 Museu Aeroespacial entidade coletiva 74 ""
A0020 Lamberg, Moritz pessoa 73 ""
A0021 Stahl, Augusto pessoa 72 ""
A0022 Barros, Justiniano José de pessoa 72 ""
A0023 Barros, Flávio de pessoa 71 ""
A0024 Holland, S. H pessoa 63 ""
A0025 Photographia Americana entidade coletiva 63 ""
A0026 Marc Ferrez & Cia entidade coletiva 62 ""
A0027 Rondon, Benjamin pessoa 62 Benjamin Rondon | [Rondon, Benjamin]
A0028 Gabinete Fotográfico da Comissão de Obras do Porto (RJ) entidade coletiva 58 ""
A0029 Pastore, Vincenzo pessoa 58 ""
A0030 Henschel, Alberto, 1827-1882 pessoa 57 Alberto Henschel | Henschel, Alberto
A0031 Gorham, Reginald pessoa 56 ""
A0032 Pinto, J., 1884-1951 pessoa 56 J. PInto | J. Pinto | Pinto, J.
A0033 Torres pessoa ou entidade 55 ""
A0034 BOSCAGLI, José pessoa 54 ""
A0035 Mendo, Ignácio F., fl. 1870 pessoa 54 ""
A0036 Krausz, Alfredo pessoa 53 ""
A0037 [s.n.] pessoa ou entidade 52 [S.N] | [s.n]
A0038 Quaas, Otto Rudolf pessoa 51 ""
A0039 Malta, Uriel, 1910-1994 pessoa 51 ""
A0040 Escola de Aeronáutica do Exército entidade coletiva 46 ""
A0041 Robin, Paul Théodore, m. 1897 pessoa 46 ""
A0042 Frisch, Albert pessoa 45 ""
A0043 Riedel, Augusto, 1836-ca.1877 pessoa 45 Riedel, Augusto
A0044 Klumb, Revert Henry, ca. 1826-ca. 1886 pessoa 44 ""
A0045 Fidanza, Felipe Augusto, ca.1847-1904 pessoa 44 Fidanza, Felipe Augusto
A0046 A. Ribeiro pessoa ou entidade 44 Ribeiro, A | Ribeiro, A.
A0047 Frond, Victor, 1821-1881 pessoa 43 Frond, Victor
A0048 Rodrigues & C°. Editores e Proprietários pessoa ou entidade 39 ""
A0049 Justa, O pessoa 38 ""
A0050 Ribeiro, Antônio Caetano da Costa pessoa 38 ""
A0051 Maison Chic pessoa ou entidade 37 ""
A0052 Musso, Luiz pessoa 37 ""
A0053 Musso & Cia entidade coletiva 37 ""
A0054 Paul Erbe pessoa ou entidade 36 ""
A0055 Guimarães, José Ferreira, 1841-1924 pessoa 36 Guimarães, José Ferreira
A0056 Horácio Coelho pessoa ou entidade 35 ""
A0057 Prugner, Gustavo pessoa 35 ""
A0058 Stahl & Cia entidade coletiva 35 ""
A0059 Teixeira, José pessoa 35 José Teixeira | Teixeira, José,
A0060 Phototypia A. Ribeiro pessoa ou entidade 33 ""
A0061 Photo Lindemann &Cª entidade coletiva 31 ""
A0062 Malta, Aristógiton, 1904-1954 pessoa 31 Malta, Aristógiton
A0063 Mulock, Benjamin Robert, 1829-1863 pessoa 31 ""
A0064 Silva, Pedro Gonsalves da pessoa 31 ""
A0065 Christiano Junior pessoa ou entidade 30 ""
A0066 Thomaz Farkas (Autoria) pessoa ou entidade 28 Thomaz Farkas
A0067 Ribeyrolles, Charles, 1812-1860 pessoa 28 ""
A0068 Vianna, José Baptista Barreira pessoa 28 ""
A0069 Christiano Junior, 1830-1902 pessoa 28 ""
A0070 Tondella, Manoel pessoa 28 ""
A0071 Amoretty, Augusto, 1845-1906 pessoa 26 Amoretty, Augusto
A0072 Huebner, George pessoa 26 ""
A0073 Vedani, Camillo pessoa 25 ""
A0074 Manuel, F. (Frédéric) pessoa 25 ""
A0075 Ferreira, Antonio Luiz pessoa 24 ""
A0076 Martins, Henrique pessoa 24 ""
A0077 Huber, Jacques (1867-1914) pessoa 24 Huber, Jacques | Jacques Huber
A0078 Julien Mandel (1893 - 1961) pessoa ou entidade 23 ""
A0079 Menezes, J pessoa 23 ""
A0080 Dietze, Albert Richard, fl. 1869 pessoa 22 ""
A0081 Parente, Nicola Maria pessoa 22 ""
A0082 Abrahão, Benjamin pessoa 22 ""
A0083 Henschel & Benque pessoa ou entidade 21 ""
A0084 Villela, João Ferreira, fl. 1861-1880 pessoa 21 Villela, João Ferreira
A0085 Photo Lopes Rio entidade coletiva 20 ""
A0086 Oswaldo Cruz pessoa ou entidade 20 Cruz, Oswaldo
A0087 Casa Leuzinger entidade coletiva 20 ""
A0088 Alkmim, Chichico pessoa 20 ""
A0089 Queiroz, Anastacio pessoa 20 ""
A0090 Lunara pessoa ou entidade 20 ""
A0091 Hees, Pedro, 1841-1880 pessoa 19 ""
A0092 Ayres, Joaquim pessoa 19 ""
A0093 José Louro pessoa ou entidade 19 ""
A0094 Preising, Theodor pessoa 18 ""
A0095 IBGE pessoa ou entidade 18 ""
A0096 Garbe, Walter pessoa 17 ""
A0097 Provável Uriel Malta pessoa ou entidade 16 ""
A0098 Thiele & Kollien pessoa ou entidade 16 ""
A0099 Pacheco, Bernardo José pessoa 16 ""
A0100 Christiano Junior E Pacheco pessoa ou entidade 16 ""
A0101 Mascarenhas, Therezio pessoa 16 ""
A0102 Photo Mortimer entidade coletiva 15 ""
A0103 Piereck, Louis, 1880-1931 pessoa 15 Piereck, Louis
A0104 Instituto de Expansão Comercial entidade coletiva 15 ""
A0105 Lobo, Antônio Araújo de Souza; Oliveira, Antônio Barbosa pessoa 15 ""
A0106 Trindade, J. S pessoa 14 ""
A0107 Oficina de Paulo Robin entidade coletiva 14 ""
A0108 H&J Tourte Éditeurs entidade coletiva 14 ""
A0109 Corrêa, J. A pessoa 14 ""
A0110 Bippus, Carlos pessoa 13 ""
A0111 Papelaria e Typographia Botelho pessoa ou entidade 13 ""
A0112 [sem autor] pessoa ou entidade 13 ""
A0113 João Stamato pessoa ou entidade 13 ""
A0114 Photographia Allemã entidade coletiva 12 Photographia Allemã (Firma)
A0115 Silva, Pio pessoa 12 ""
A0116 Benoist, Philippe, 1813-1905 pessoa 12 ""
A0117 LTM (Firma) pessoa ou entidade 12 LTM
A0118 Fidanza, Filipe Augusto, fl. 1861-1920 pessoa 12 ""
A0119 Tondella, Manoel, Photografia Tondella pessoa 12 ""
A0120 Garcia, F pessoa 11 ""
A0121 Subcomissão de Estudos dos Portos de Fortaleza e Camocim (CE) pessoa ou entidade 11 ""
A0122 Mulock, Benjamin pessoa 11 ""
A0123 Christiano Jr. & Pacheco pessoa ou entidade 11 ""
A0124 William Notman pessoa ou entidade 11 ""
A0125 Centennial Photographic Co pessoa ou entidade 11 ""
A0126 Boote, Samuel, 1844-1921 pessoa 11 ""
A0127 Costa, Hermina de Carvalho Menna da, 18- -19- pessoa 10 ""
A0128 Terragno, Luiz pessoa 10 ""
A0129 Joaquim Insley Pacheco (Autoria) pessoa ou entidade 10 ""
A0130 Lohse, Ernst (1873-1930) pessoa 10 ""
A0131 Bocage, Francisco du pessoa 10 ""
A0132 Lindemann, Rodolpho pessoa 10 ""
A0133 Jacottet, Louis-Julien, 1806-1880 pessoa 10 ""
A0134 Biblioteca Nacional (Brasil) entidade coletiva 10 ""
A0135 Carneiro & Gaspar pessoa ou entidade 10 ""
A0136 Editores & propriedade de Rodrigues & Co. Rua do Ouvidor, 57 pessoa 10 ""
A0137 Passos, Elysio Pereira dos pessoa 9 ""
A0138 Wessel pessoa ou entidade 9 ""
A0139 Moura, Miguel de, 1883- pessoa 9 Moura, Miguel de, n. 1883
A0140 Florence, Hercule pessoa 9 ""
A0141 Niemeyer, Louis pessoa 9 ""
A0142 The Aircraft Operating Co. Ltd pessoa ou entidade 8 ""
A0143 Hagmann, Gottfried (1874-1946) pessoa 8 ""
A0144 Goston, João pessoa 8 ""
A0145 Sorrieu, Frédéric, n. 1807 pessoa 8 ""
A0146 Champagne pessoa ou entidade 8 ""
A0147 Lima, Eudozio pessoa 8 ""
A0148 Bate E Cia entidade coletiva 8 ""
A0149 Huebner & Amaral pessoa ou entidade 8 ""
A0150 Photo Bippus entidade coletiva 8 ""
A0151 Rosen, Henrique, m. 1892 pessoa 8 ""
A0152 Peixoto, Antonio Carlos de Sampaio, m. 1914 pessoa 8 ""
A0153 King, John pessoa 7 ""
A0154 Angelo Regato (Fotógrafo) pessoa ou entidade 7 ""
A0155 Leuzinger, George, 1813-1892 pessoa 7 ""
A0156 Perez, M pessoa 7 ""
A0157 Martineau, Willian pessoa 7 ""
A0158 Musso, Luís, [? -1908] pessoa 7 ""
A0159 Carvalho, Alfredo Climaco de pessoa 7 ""
A0160 Tondella, Manoel, Photographia Tondella entidade coletiva 7 ""
A0161 Moraites, P pessoa 7 ""
A0162 Scheidemantel, Bernardo, 1834-1908 pessoa 7 ""
A0163 Affonso, José dos Santos pessoa 6 ""
A0164 G. Leuzinger & Filhos pessoa ou entidade 6 ""
A0165 Wanderley, Luiz Lavenère pessoa 6 ""
A0166 Gomes Junior pessoa ou entidade 6 ""
A0167 Destacamento de Aviação de Curitiba entidade coletiva 6 ""
A0168 Photo Bippus Rio entidade coletiva 6 ""
A0169 Photo Rotativo entidade coletiva 5 ""
A0170 Thiele pessoa ou entidade 5 ""
A0171 Silva, Paulo Bracy Gama da pessoa 5 ""
A0172 Photographia Artística de Miguel de Moura entidade coletiva 5 ""
A0173 Stahl & Wahnschaffe pessoa ou entidade 5 ""
A0174 Coutinho, Abilio pessoa 5 ""
A0175 Silva, Ezequiel pessoa 5 ""
A0176 Barza, Constantino pessoa 5 ""
A0177 Bianchi, Luis, 1876-1940 pessoa 5 ""
A0178 Lavenère, L pessoa 5 ""
A0179 J. J Oliveira, Manoel Tondella pessoa 5 ""
A0180 Lombaerts & Comp. Editores pessoa ou entidade 4 ""
A0181 Keller, Franz, 1835-1890 pessoa 4 Keller, Franz
A0182 Van Nyvel, Guimarães & C pessoa 4 ""
A0183 Silva, Arsenio da pessoa 4 ""
A0184 Büsch, Fritz pessoa 4 ""
A0185 Duruy, A. (Alexandre), fl. 1845-1881 pessoa 4 ""
A0186 Charpentier pessoa ou entidade 4 ""
A0187 Ateliers D. A. Longuet Imp. Phot pessoa ou entidade 4 ""
A0188 Ducasble, Alfredo pessoa 4 ""
A0189 Frisch, Christoph Albert, 1840-1918 pessoa 4 ""
A0190 Calcagno, Luiz Bartolomeu pessoa 4 ""
A0191 Cardoso, Antônio Lopes pessoa 4 ""
A0192 Pedro Le Houërou Photographo pessoa ou entidade 4 ""
A0193 Skarke, Fernando pessoa 4 ""
A0194 Livraria Lombaerts & C pessoa ou entidade 3 ""
A0195 Soper, Fred Lowe, 1893-1977 pessoa 3 ""
A0196 Monnerat, Roberto Mario pessoa 3 ""
A0197 Law, Henry, 1824-1900 pessoa 3 ""
A0198 Paranaguá, Francisco Vilela Barbosa, Marquês de, 1769-1846 pessoa 3 ""
A0199 Mora (Fotógrafo) pessoa ou entidade 3 ""
A0200 G. & A. Overbeck pessoa ou entidade 3 G & A Overbeck | G&A Overbeck
A0201 Glaziou, Auguste François Marie, 1833-1897 pessoa 3 ""
A0202 Cesar, Carlos pessoa 3 ""
A0203 Cunha, Silvio pessoa 3 ""
A0204 Archanjo Sobrinho pessoa ou entidade 3 ""
A0205 Lobo, A. de Barros pessoa 2 ""
A0206 Barreiros, A pessoa 2 ""
A0207 Lombaerts & Comp., Editores pessoa 2 ""
A0208 Izabel Jacintha Reeckell pessoa ou entidade 2 ""
A0209 Madame Reeckell pessoa ou entidade 2 ""
A0210 Eduardo de Los Rios pessoa ou entidade 2 ""
A0211 Photo Weiss- Estúdio/Agência entidade coletiva 2 Photo Weiss - Estúdio/Agência
A0212 Museu Aero Espacial entidade coletiva 2 ""
A0213 Soucasaux, Francisco pessoa 2 ""
A0214 Photographia Atayama entidade coletiva 2 ""
A0215 Comissão de desobstrução dos rios da Baixada Fluminense (RJ) entidade coletiva 2 ""
A0216 Dias, Bastos pessoa 2 ""
A0217 Costa, Osvaldo Gilson Fonseca, 1948 pessoa 2 ""
A0218 Campos, Augusto César Malta de, 1864-1957 pessoa 2 ""
A0219 Horacio Coppola pessoa ou entidade 2 ""
A0220 Rossi, Giulio, 1824-1884 pessoa 2 ""
A0221 Marcel Gautherot pessoa ou entidade 2 ""
A0222 Gioconda Rizzo pessoa ou entidade 2 ""
A0223 Braz pessoa ou entidade 2 ""
A0224 Laurens, J pessoa 2 ""
A0225 Laurens, Jules-Joseph-Augustin, 1825-1901 pessoa 2 ""
A0226 Bernieri, J pessoa 2 ""
A0227 Sommer, Giorgio, 1834-1914 pessoa 2 ""
A0228 Pacheco & Filho pessoa ou entidade 2 PACHECO & FILHO
A0229 Schleier J pessoa ou entidade 2 ""
A0230 Lewis, John C. A pessoa 2 ""
A0231 Moreira, Archimedes pessoa 2 ""
A0232 Vannini, N pessoa 2 ""
A0233 Fragoso, Armando pessoa 2 ""
A0234 Huberti (Fotógrafo) pessoa ou entidade 2 Huberti
A0235 Barboza, João de Almeida pessoa 2 ""
A0236 Firpo, João pessoa 2 ""
A0237 Forni, Agostino pessoa 2 ""
A0238 Trebby, Frederico pessoa 2 ""
A0239 Galeria Universal de Carlos Cesar pessoa ou entidade 2 ""
A0240 Trebby y Cia entidade coletiva 2 ""
A0241 Filgueiras, A pessoa 2 ""
A0242 Sá, Gazzi de, 1901-1981 pessoa 2 ""
A0243 Fernandes, Gonçalves, 1909-1986 pessoa 2 ""
A0244 A. Filgueiras Photo Amador entidade coletiva 2 ""
A0245 Agfa Tropex pessoa ou entidade 2 ""
A0246 Aliwu pessoa ou entidade 2 ""
A0247 Ultzmann, Robert, 1842-1889 pessoa 2 ""
A0248 Benque, Francisco e Henschel, Alberto pessoa 2 ""
A0249 Carneiro, Joaquim Feliciano Alves e Tavares pessoa 2 ""
A0250 Lobo, Antônio Araújo de Souza pessoa 2 ""
A0251 Oliveira, Antônio Barbosa pessoa 2 ""
A0252 Pinto. J pessoa ou entidade 2 ""
A0253 Ducasble, Alfredo | Fotografia Parisienne entidade coletiva 2 ""
A0254 Soucasaux, Augusto pessoa 2 ""
A0255 s/nome pessoa ou entidade 2 ""
A0256 Photographia Popular Oliveira & Tondella entidade coletiva 2 ""
A0257 Tondella, Manoel. Photografia Tondella pessoa 2 ""
A0258 Du Bocage, F., F. Du Bocage Photographia entidade coletiva 2 ""
A0259 Mello, Borges de, Photographia modelo Borges de Mello entidade coletiva 2 ""
A0260 1º Comando do Exército entidade coletiva 2 ""
A0261 Silveira, J pessoa 2 ""
A0262 Guimarães, Antonio de Oliveira pessoa 2 ""
A0263 Furne fils et H. Tournier pessoa ou entidade 2 ""
A0264 Carneiro & Smith pessoa ou entidade 2 ""
A0265 Sabino pessoa ou entidade 2 ""
A0266 Arthur e J. J. Wischral pessoa ou entidade 2 ""
A0267 A. C. da Costa Ribeiro pessoa ou entidade 2 ""
A0268 Pittigliani, Armando pessoa 2 ""
A0269 Photographia Marc Ferrez entidade coletiva 2 ""
A0270 Sobrosa Rio pessoa ou entidade 1 ""
A0271 Sobrosa, Antenor pessoa 1 ""
A0272 José Francisco Corrêa et C pessoa ou entidade 1 ""
A0273 Corrêa, José Francisco pessoa 1 ""
A0274 Castro, Jorge de pessoa 1 ""
A0275 Duarte, B. J. (Benedito Junqueira), 1910-1995 pessoa 1 ""
A0276 Vosylius, Kazys pessoa 1 ""
A0277 Leon de Rennes pessoa ou entidade 1 ""
A0278 Foto aérea Campo Marinha no Galeão entidade coletiva 1 ""
A0279 Lopes pessoa ou entidade 1 ""
A0280 Nicola Parente pessoa ou entidade 1 ""
A0281 Ferrez, Luciano (1884 - 1955) pessoa 1 ""
A0282 Jean Manzon pessoa ou entidade 1 ""
A0283 Valuos, Guilherme pessoa 1 ""
A0284 Viggiani, N pessoa 1 ""
A0285 Dutra, Olavo - Fotógrafo pessoa 1 ""
A0286 Fotógrafo: Vernaut, Benjamin pessoa 1 ""
A0287 Photographia Guimarães entidade coletiva 1 ""
A0288 E. Av. M pessoa ou entidade 1 ""
A0289 Monteiro, Augusto pessoa 1 ""
A0290 Stille, Paul pessoa 1 ""
A0291 cios e préTheodor pessoa ou entidade 1 ""
A0292 [Otto Hees?] pessoa ou entidade 1 ""
A0293 Studio Paul entidade coletiva 1 ""
A0294 Dr. Menescal pessoa ou entidade 1 ""
A0295 Rembrandt - Rio pessoa ou entidade 1 ""
A0296 Bellati, R. (Fotógrafo) pessoa 1 ""
A0297 Somlo, Tomas pessoa 1 ""
A0298 Emerico pessoa ou entidade 1 ""
A0299 Carlos Moskovics pessoa ou entidade 1 ""
A0300 Musso, Luís, m. 1908 pessoa 1 ""
A0301 Agência Nacional entidade coletiva 1 ""
A0302 Walery pessoa ou entidade 1 ""
A0303 Klumb, Henrique Revert pessoa 1 ""
A0304 Coutinho, A pessoa 1 ""
A0305 Clerget pessoa ou entidade 1 ""
A0306 Adam, Victor Jean, 1801-1866 pessoa 1 ""
A0307 Courtois, J pessoa 1 ""
A0308 Mason, Samuel J pessoa 1 ""
A0309 Bradley & Rulofson pessoa ou entidade 1 ""
A0310 H. Delie and E. Bechard pessoa ou entidade 1 ""
A0311 Noël, Alphonse Léon, 1807-1884 pessoa 1 ""
A0312 Helios (Fotógrafo) pessoa ou entidade 1 ""
A0313 Nadar, Felix, 1820-1910 pessoa 1 ""
A0314 Photographia Popular entidade coletiva 1 ""
A0315 Angerer, Ludwig, 1827-1879 pessoa 1 ""
A0316 Schoefft, O pessoa 1 ""
A0317 Mourgeon, C pessoa 1 ""
A0318 Antunes, F pessoa 1 ""
A0319 Aguiar, Francisco Marcellino de Souza, 1855-1935 pessoa 1 ""
A0320 Marc Ferrez & Filhos pessoa ou entidade 1 ""
A0321 Zaccaria, G pessoa 1 ""
A0322 Photograhia Vesuvio de Nicola Maria Parente pessoa ou entidade 1 ""
A0323 Silveira, Pedro Satyro de Souza da pessoa 1 ""
A0324 Rocha, J. C. da pessoa 1 ""
A0325 Photographia Americana de Moreira & Roltgen entidade coletiva 1 ""
A0326 Moreira & Roltgen pessoa ou entidade 1 ""
A0327 Lopes & Ca pessoa ou entidade 1 ""
A0328 Photographia Imperial de Lopes & Ca entidade coletiva 1 ""
A0329 Atelier Photograhico Hygino Soares entidade coletiva 1 ""
A0330 Nunes, Henrique, 1820-1895 pessoa 1 ""
A0331 Luys, Jules Bernard, 1828-1897 pessoa 1 ""
A0332 Wegner & Mottu pessoa ou entidade 1 ""
A0333 Brogi, Giacomo, 1822-1881 pessoa 1 ""
A0334 Con, Frederico Carlos pessoa 1 ""
A0335 Fenton, Roger, 1819-1869 pessoa 1 ""
A0336 Banchieri, Manoel pessoa 1 ""
A0337 Fratelli Alinari Fotografi pessoa ou entidade 1 ""
A0338 Photographie Technique A. Fernique pessoa ou entidade 1 ""
A0339 Typographia Imperial & Real de Vienna pessoa ou entidade 1 ""
A0340 Clairin, Georges-Jules-Victor, 1843-1919 pessoa 1 ""
A0341 Gilleta & Gilly pessoa ou entidade 1 ""
A0342 Arena, Giacomo, 1818-1906 pessoa 1 ""
A0343 Jerace, Francesco, 1854 - 1937 pessoa 1 ""
A0344 Calzolari, Icilio pessoa 1 ""
A0345 Fumeo, Pietro, 1831-1898 pessoa 1 ""
A0346 Trinquart (Fotógrafo) pessoa ou entidade 1 ""
A0347 Berthier, Paul, 1822-1912 pessoa 1 ""
A0348 Albert, Joseph, 1825-1886 pessoa 1 ""
A0349 Photographie Americaine pessoa ou entidade 1 ""
A0350 Kaun Phot pessoa ou entidade 1 ""
A0351 Mauritshuis (Haia, Holanda) pessoa 1 ""
A0352 Salentin, Hubert, 1822-1910 pessoa 1 ""
A0353 Boker, Carl, 1836-1905 pessoa 1 ""
A0354 Sonderland, F, 1836-1896 pessoa 1 ""
A0355 C. & A. Overbeck pessoa ou entidade 1 ""
A0356 Bosch, E pessoa 1 ""
A0357 Werff, Adriaen van der, 1659 - 1722 pessoa 1 ""
A0358 Gleyre, Charles, 1806-1874 pessoa 1 ""
A0359 Goupil & Cie pessoa ou entidade 1 ""
A0360 Stacey, C.A pessoa 1 ""
A0361 Draper, Henry, 1837-1882 pessoa 1 ""
A0362 Ludwig, Johann Fridrich, 1670-1752 pessoa 1 ""
A0363 Meireles, Vítor, 1832-1903 pessoa 1 ""
A0364 José da Santíssima Trindade, Bispo, 1762-1835 pessoa 1 ""
A0365 Lucarell, Mario pessoa 1 ""
A0366 Costa, Heitor da Silva, 1837-1947 pessoa 1 ""
A0367 Foto Lucarelli entidade coletiva 1 ""
A0368 Lima, José Otávio Correia, 1878-1974 pessoa 1 ""
A0369 Read, R. A pessoa 1 ""
A0370 Severino (Fotógrafo) pessoa ou entidade 1 ""
A0371 Hospe, Joseph pessoa 1 ""
A0372 Photo Lindemann entidade coletiva 1 ""
A0373 Conti, José Carlos pessoa 1 ""
A0374 Photo Studio Huberti entidade coletiva 1 ""
A0375 Boquel, Julien pessoa 1 ""
A0376 Silva, M. Nogueira da pessoa 1 ""
A0377 Hoenen, Carlos pessoa 1 ""
A0378 Fábrica de Ferro de Ipanema pessoa ou entidade 1 ""
A0379 Rio Branco, José Maria da Silva Paranhos, Barão do, 1845-1912 pessoa 1 ""
A0380 Nickelsen (Fotógrafo) pessoa ou entidade 1 ""
A0381 Lima, Antonio Mariano de, 1858-1902 pessoa 1 ""
A0382 Mello, Affonso de Oliveira pessoa 1 ""
A0383 Lavinthal, Joaquim Ferreira dos Santos pessoa 1 ""
A0384 Photo Lavinthal entidade coletiva 1 ""
A0385 Vieira, Valério, 1862-1941 pessoa 1 ""
A0386 Bate & Cia entidade coletiva 1 ""
A0387 Micheles (Fotógrafo) pessoa ou entidade 1 ""
A0388 Rochet, Louis, 1813-1878 pessoa 1 ""
A0389 Mafra, João Maximiniano pessoa 1 ""
A0390 Fleury, André Augusto de Pádua, 1830-1895 pessoa 1 ""
A0391 Faro, Gonçalo Paes de Azevedo, 1846-1900 pessoa 1 ""
A0392 Liais, Emmanuel, 1826-1900 pessoa 1 ""
A0393 Hermida Pazos, José, 1829-1921 pessoa 1 ""
A0394 Aquidabã pessoa ou entidade 1 ""
A0395 Oliveira, C. de pessoa 1 ""
A0396 Oliveira, Candido Marinho pessoa 1 ""
A0397 Satrap Photo entidade coletiva 1 ""
A0398 Agfa Brovira pessoa ou entidade 1 ""
A0399 Ferrez, Gilberto pessoa 1 ""
A0400 Boute pessoa ou entidade 1 ""
A0401 Buvelot & Prat pessoa ou entidade 1 ""
A0402 Panigai, Marco di pessoa 1 ""
A0403 David Latino & Franklin pessoa ou entidade 1 ""
A0404 Leuthold e Dursky pessoa ou entidade 1 ""
A0405 Antunes, Humberto Saraiva pessoa 1 ""
A0406 Castro pessoa ou entidade 1 ""
A0407 Comp. Lith. Hartmann-Reichenbach entidade coletiva 1 ""
A0408 Photographia Guilherme Gaensly entidade coletiva 1 ""
A0409 Papeleria Travassos pessoa ou entidade 1 ""
A0410 Phototipie Marius Bar pessoa ou entidade 1 ""
A0411 Bureu Poste pessoa ou entidade 1 ""
A0412 Edição A. Moura pessoa ou entidade 1 ""
A0413 Bureau Poste pessoa ou entidade 1 ""
A0414 Ao Cantineiro Naval pessoa ou entidade 1 ""
A0415 Henschel e Benque pessoa ou entidade 1 ""
A0416 Mello, Marcos A. de pessoa 1 ""
A0417 Soares, José Severino pessoa 1 ""
A0418 Bastos, A pessoa 1 ""
A0419 Henschel, Albert, 1827-1882 pessoa 1 ""
A0420 Bonfioti, J pessoa 1 ""
A0421 Foto Chic entidade coletiva 1 ""
A0422 Barboza, Theotonio pessoa 1 ""
A0423 Rogato, Guilherme pessoa 1 ""
A0424 Photo Skarke entidade coletiva 1 ""
A0425 Serviço Photographico de Vida Domestica entidade coletiva 1 ""
A0426 Foto Studio Gloria entidade coletiva 1 ""
A0427 Fotografia Alemã entidade coletiva 1 ""
A0428 Brady, Mathew B., ca. 1823-1896 pessoa 1 ""
A0429 Photograhia Popular Oliveira & Tondella pessoa ou entidade 1 ""
A0430 Photografia Popular Oliveira & Tondella pessoa ou entidade 1 ""
A0431 Manoel Tondella, Photografia Tondella pessoa 1 ""
A0432 Claude Lévi-Strauss pessoa ou entidade 1 ""
A0433 Monteiro,Photographie Chic Monteiro & C pessoa 1 ""
A0434 Edgard Egydio de Souza pessoa ou entidade 1 ""
A0435 S/A pessoa ou entidade 1 ""
A0436 Chapelin E Pereira pessoa ou entidade 1 ""
A0437 Poluceno & Pinho pessoa ou entidade 1 ""
A0438 <ns:Co & Pinho pessoa ou entidade 1 ""
A0439 Thiele & Kollien [?]; Photo Bippus Rio [?] entidade coletiva 1 ""
A0440 Photographia Central entidade coletiva 1 ""
A0441 Veiga, Bernardo Saturnino da pessoa 1 ""
A0442 Phototypie Berthaud pessoa ou entidade 1 ""
A0443 Marinho, P pessoa 1 ""
A0444 A. Editora entidade coletiva 1 ""
A0445 511-73, Marc pessoa 1 ""
A0446 J. Stamato pessoa ou entidade 1 ""
A0447 DADE pessoa ou entidade 1 ""
A0448 Annunciato pessoa ou entidade 1 ""
A0449 Benque pessoa ou entidade 1 ""
A0450 Chapelin pessoa ou entidade 1 ""
A0451 Scheidemantel, B pessoa 1 ""
A0452 Photo Braz Rio entidade coletiva 1 ""
A0453 Scheuenstuhl, Paulo pessoa 1 ""
A0454 Caras & Caretas pessoa ou entidade 1 ""
A0455 Leonar pessoa ou entidade 1 ""
A0456 Azevedo, J. Faria de pessoa 1 ""
A0457 Basto, F pessoa 1 ""
1 id forma_autorizada tipo ocorrencias variantes
2 A0001 Ferrez, Marc, 1843-1923 pessoa 1960 Ferrez, Marc | Marc Ferrez | Marc Ferrez (Autoria)
3 A0002 Malta, Augusto, 1864-1957 pessoa 1175 Augusto Malta | MALTA, Augusto | Malta, Augusto | Malta, Augusto,1864-1957
4 A0003 Escola de Aviação Militar entidade coletiva 596
5 A0004 Santos, Guilherme pessoa 420
6 A0005 Gutierrez, Juan, 1859-1897 pessoa 373 Gutierrez, Juan | Gutierrez, Juan, m. 1897
7 A0006 Kfuri, Jorge, 1893-1965 pessoa 294 Kfuri, Jorge
8 A0007 Klumb, Revert Henrique, fl. 1855-1880 pessoa 290 Klumb, Revert Henrique
9 A0008 Leuzinger, Georges pessoa 257
10 A0009 Escola de Aeronáutica entidade coletiva 174
11 A0010 Officina de Paulo Robin entidade coletiva 169
12 A0011 Robin, Paulo, m. 1897 pessoa 158
13 A0012 Photographia Brazileira entidade coletiva 126
14 A0013 Wischral, Arthur pessoa 124
15 A0014 Gaensly, Guilherme, 1843-1928 pessoa 123 Gaensly, Guilherme
16 A0015 Escola de Aeronáutica Militar entidade coletiva 88
17 A0016 Merrill, D. B. (Dana B.) pessoa 86
18 A0017 Pacheco, Joaquim Insley, 1830-1912 pessoa 82 Pacheco, Joaquim Insley | Pacheco, Joaquim Insley, m. 1912
19 A0018 Azevedo, Militão Augusto de pessoa 75
20 A0019 Museu Aeroespacial entidade coletiva 74
21 A0020 Lamberg, Moritz pessoa 73
22 A0021 Stahl, Augusto pessoa 72
23 A0022 Barros, Justiniano José de pessoa 72
24 A0023 Barros, Flávio de pessoa 71
25 A0024 Holland, S. H pessoa 63
26 A0025 Photographia Americana entidade coletiva 63
27 A0026 Marc Ferrez & Cia entidade coletiva 62
28 A0027 Rondon, Benjamin pessoa 62 Benjamin Rondon | [Rondon, Benjamin]
29 A0028 Gabinete Fotográfico da Comissão de Obras do Porto (RJ) entidade coletiva 58
30 A0029 Pastore, Vincenzo pessoa 58
31 A0030 Henschel, Alberto, 1827-1882 pessoa 57 Alberto Henschel | Henschel, Alberto
32 A0031 Gorham, Reginald pessoa 56
33 A0032 Pinto, J., 1884-1951 pessoa 56 J. PInto | J. Pinto | Pinto, J.
34 A0033 Torres pessoa ou entidade 55
35 A0034 BOSCAGLI, José pessoa 54
36 A0035 Mendo, Ignácio F., fl. 1870 pessoa 54
37 A0036 Krausz, Alfredo pessoa 53
38 A0037 [s.n.] pessoa ou entidade 52 [S.N] | [s.n]
39 A0038 Quaas, Otto Rudolf pessoa 51
40 A0039 Malta, Uriel, 1910-1994 pessoa 51
41 A0040 Escola de Aeronáutica do Exército entidade coletiva 46
42 A0041 Robin, Paul Théodore, m. 1897 pessoa 46
43 A0042 Frisch, Albert pessoa 45
44 A0043 Riedel, Augusto, 1836-ca.1877 pessoa 45 Riedel, Augusto
45 A0044 Klumb, Revert Henry, ca. 1826-ca. 1886 pessoa 44
46 A0045 Fidanza, Felipe Augusto, ca.1847-1904 pessoa 44 Fidanza, Felipe Augusto
47 A0046 A. Ribeiro pessoa ou entidade 44 Ribeiro, A | Ribeiro, A.
48 A0047 Frond, Victor, 1821-1881 pessoa 43 Frond, Victor
49 A0048 Rodrigues & C°. Editores e Proprietários pessoa ou entidade 39
50 A0049 Justa, O pessoa 38
51 A0050 Ribeiro, Antônio Caetano da Costa pessoa 38
52 A0051 Maison Chic pessoa ou entidade 37
53 A0052 Musso, Luiz pessoa 37
54 A0053 Musso & Cia entidade coletiva 37
55 A0054 Paul Erbe pessoa ou entidade 36
56 A0055 Guimarães, José Ferreira, 1841-1924 pessoa 36 Guimarães, José Ferreira
57 A0056 Horácio Coelho pessoa ou entidade 35
58 A0057 Prugner, Gustavo pessoa 35
59 A0058 Stahl & Cia entidade coletiva 35
60 A0059 Teixeira, José pessoa 35 José Teixeira | Teixeira, José,
61 A0060 Phototypia A. Ribeiro pessoa ou entidade 33
62 A0061 Photo Lindemann &Cª entidade coletiva 31
63 A0062 Malta, Aristógiton, 1904-1954 pessoa 31 Malta, Aristógiton
64 A0063 Mulock, Benjamin Robert, 1829-1863 pessoa 31
65 A0064 Silva, Pedro Gonsalves da pessoa 31
66 A0065 Christiano Junior pessoa ou entidade 30
67 A0066 Thomaz Farkas (Autoria) pessoa ou entidade 28 Thomaz Farkas
68 A0067 Ribeyrolles, Charles, 1812-1860 pessoa 28
69 A0068 Vianna, José Baptista Barreira pessoa 28
70 A0069 Christiano Junior, 1830-1902 pessoa 28
71 A0070 Tondella, Manoel pessoa 28
72 A0071 Amoretty, Augusto, 1845-1906 pessoa 26 Amoretty, Augusto
73 A0072 Huebner, George pessoa 26
74 A0073 Vedani, Camillo pessoa 25
75 A0074 Manuel, F. (Frédéric) pessoa 25
76 A0075 Ferreira, Antonio Luiz pessoa 24
77 A0076 Martins, Henrique pessoa 24
78 A0077 Huber, Jacques (1867-1914) pessoa 24 Huber, Jacques | Jacques Huber
79 A0078 Julien Mandel (1893 - 1961) pessoa ou entidade 23
80 A0079 Menezes, J pessoa 23
81 A0080 Dietze, Albert Richard, fl. 1869 pessoa 22
82 A0081 Parente, Nicola Maria pessoa 22
83 A0082 Abrahão, Benjamin pessoa 22
84 A0083 Henschel & Benque pessoa ou entidade 21
85 A0084 Villela, João Ferreira, fl. 1861-1880 pessoa 21 Villela, João Ferreira
86 A0085 Photo Lopes Rio entidade coletiva 20
87 A0086 Oswaldo Cruz pessoa ou entidade 20 Cruz, Oswaldo
88 A0087 Casa Leuzinger entidade coletiva 20
89 A0088 Alkmim, Chichico pessoa 20
90 A0089 Queiroz, Anastacio pessoa 20
91 A0090 Lunara pessoa ou entidade 20
92 A0091 Hees, Pedro, 1841-1880 pessoa 19
93 A0092 Ayres, Joaquim pessoa 19
94 A0093 José Louro pessoa ou entidade 19
95 A0094 Preising, Theodor pessoa 18
96 A0095 IBGE pessoa ou entidade 18
97 A0096 Garbe, Walter pessoa 17
98 A0097 Provável Uriel Malta pessoa ou entidade 16
99 A0098 Thiele & Kollien pessoa ou entidade 16
100 A0099 Pacheco, Bernardo José pessoa 16
101 A0100 Christiano Junior E Pacheco pessoa ou entidade 16
102 A0101 Mascarenhas, Therezio pessoa 16
103 A0102 Photo Mortimer entidade coletiva 15
104 A0103 Piereck, Louis, 1880-1931 pessoa 15 Piereck, Louis
105 A0104 Instituto de Expansão Comercial entidade coletiva 15
106 A0105 Lobo, Antônio Araújo de Souza; Oliveira, Antônio Barbosa pessoa 15
107 A0106 Trindade, J. S pessoa 14
108 A0107 Oficina de Paulo Robin entidade coletiva 14
109 A0108 H&J Tourte Éditeurs entidade coletiva 14
110 A0109 Corrêa, J. A pessoa 14
111 A0110 Bippus, Carlos pessoa 13
112 A0111 Papelaria e Typographia Botelho pessoa ou entidade 13
113 A0112 [sem autor] pessoa ou entidade 13
114 A0113 João Stamato pessoa ou entidade 13
115 A0114 Photographia Allemã entidade coletiva 12 Photographia Allemã (Firma)
116 A0115 Silva, Pio pessoa 12
117 A0116 Benoist, Philippe, 1813-1905 pessoa 12
118 A0117 LTM (Firma) pessoa ou entidade 12 LTM
119 A0118 Fidanza, Filipe Augusto, fl. 1861-1920 pessoa 12
120 A0119 Tondella, Manoel, Photografia Tondella pessoa 12
121 A0120 Garcia, F pessoa 11
122 A0121 Subcomissão de Estudos dos Portos de Fortaleza e Camocim (CE) pessoa ou entidade 11
123 A0122 Mulock, Benjamin pessoa 11
124 A0123 Christiano Jr. & Pacheco pessoa ou entidade 11
125 A0124 William Notman pessoa ou entidade 11
126 A0125 Centennial Photographic Co pessoa ou entidade 11
127 A0126 Boote, Samuel, 1844-1921 pessoa 11
128 A0127 Costa, Hermina de Carvalho Menna da, 18- -19- pessoa 10
129 A0128 Terragno, Luiz pessoa 10
130 A0129 Joaquim Insley Pacheco (Autoria) pessoa ou entidade 10
131 A0130 Lohse, Ernst (1873-1930) pessoa 10
132 A0131 Bocage, Francisco du pessoa 10
133 A0132 Lindemann, Rodolpho pessoa 10
134 A0133 Jacottet, Louis-Julien, 1806-1880 pessoa 10
135 A0134 Biblioteca Nacional (Brasil) entidade coletiva 10
136 A0135 Carneiro & Gaspar pessoa ou entidade 10
137 A0136 Editores & propriedade de Rodrigues & Co. Rua do Ouvidor, 57 pessoa 10
138 A0137 Passos, Elysio Pereira dos pessoa 9
139 A0138 Wessel pessoa ou entidade 9
140 A0139 Moura, Miguel de, 1883- pessoa 9 Moura, Miguel de, n. 1883
141 A0140 Florence, Hercule pessoa 9
142 A0141 Niemeyer, Louis pessoa 9
143 A0142 The Aircraft Operating Co. Ltd pessoa ou entidade 8
144 A0143 Hagmann, Gottfried (1874-1946) pessoa 8
145 A0144 Goston, João pessoa 8
146 A0145 Sorrieu, Frédéric, n. 1807 pessoa 8
147 A0146 Champagne pessoa ou entidade 8
148 A0147 Lima, Eudozio pessoa 8
149 A0148 Bate E Cia entidade coletiva 8
150 A0149 Huebner & Amaral pessoa ou entidade 8
151 A0150 Photo Bippus entidade coletiva 8
152 A0151 Rosen, Henrique, m. 1892 pessoa 8
153 A0152 Peixoto, Antonio Carlos de Sampaio, m. 1914 pessoa 8
154 A0153 King, John pessoa 7
155 A0154 Angelo Regato (Fotógrafo) pessoa ou entidade 7
156 A0155 Leuzinger, George, 1813-1892 pessoa 7
157 A0156 Perez, M pessoa 7
158 A0157 Martineau, Willian pessoa 7
159 A0158 Musso, Luís, [? -1908] pessoa 7
160 A0159 Carvalho, Alfredo Climaco de pessoa 7
161 A0160 Tondella, Manoel, Photographia Tondella entidade coletiva 7
162 A0161 Moraites, P pessoa 7
163 A0162 Scheidemantel, Bernardo, 1834-1908 pessoa 7
164 A0163 Affonso, José dos Santos pessoa 6
165 A0164 G. Leuzinger & Filhos pessoa ou entidade 6
166 A0165 Wanderley, Luiz Lavenère pessoa 6
167 A0166 Gomes Junior pessoa ou entidade 6
168 A0167 Destacamento de Aviação de Curitiba entidade coletiva 6
169 A0168 Photo Bippus Rio entidade coletiva 6
170 A0169 Photo Rotativo entidade coletiva 5
171 A0170 Thiele pessoa ou entidade 5
172 A0171 Silva, Paulo Bracy Gama da pessoa 5
173 A0172 Photographia Artística de Miguel de Moura entidade coletiva 5
174 A0173 Stahl & Wahnschaffe pessoa ou entidade 5
175 A0174 Coutinho, Abilio pessoa 5
176 A0175 Silva, Ezequiel pessoa 5
177 A0176 Barza, Constantino pessoa 5
178 A0177 Bianchi, Luis, 1876-1940 pessoa 5
179 A0178 Lavenère, L pessoa 5
180 A0179 J. J Oliveira, Manoel Tondella pessoa 5
181 A0180 Lombaerts & Comp. Editores pessoa ou entidade 4
182 A0181 Keller, Franz, 1835-1890 pessoa 4 Keller, Franz
183 A0182 Van Nyvel, Guimarães & C pessoa 4
184 A0183 Silva, Arsenio da pessoa 4
185 A0184 Büsch, Fritz pessoa 4
186 A0185 Duruy, A. (Alexandre), fl. 1845-1881 pessoa 4
187 A0186 Charpentier pessoa ou entidade 4
188 A0187 Ateliers D. A. Longuet Imp. Phot pessoa ou entidade 4
189 A0188 Ducasble, Alfredo pessoa 4
190 A0189 Frisch, Christoph Albert, 1840-1918 pessoa 4
191 A0190 Calcagno, Luiz Bartolomeu pessoa 4
192 A0191 Cardoso, Antônio Lopes pessoa 4
193 A0192 Pedro Le Houërou Photographo pessoa ou entidade 4
194 A0193 Skarke, Fernando pessoa 4
195 A0194 Livraria Lombaerts & C pessoa ou entidade 3
196 A0195 Soper, Fred Lowe, 1893-1977 pessoa 3
197 A0196 Monnerat, Roberto Mario pessoa 3
198 A0197 Law, Henry, 1824-1900 pessoa 3
199 A0198 Paranaguá, Francisco Vilela Barbosa, Marquês de, 1769-1846 pessoa 3
200 A0199 Mora (Fotógrafo) pessoa ou entidade 3
201 A0200 G. & A. Overbeck pessoa ou entidade 3 G & A Overbeck | G&A Overbeck
202 A0201 Glaziou, Auguste François Marie, 1833-1897 pessoa 3
203 A0202 Cesar, Carlos pessoa 3
204 A0203 Cunha, Silvio pessoa 3
205 A0204 Archanjo Sobrinho pessoa ou entidade 3
206 A0205 Lobo, A. de Barros pessoa 2
207 A0206 Barreiros, A pessoa 2
208 A0207 Lombaerts & Comp., Editores pessoa 2
209 A0208 Izabel Jacintha Reeckell pessoa ou entidade 2
210 A0209 Madame Reeckell pessoa ou entidade 2
211 A0210 Eduardo de Los Rios pessoa ou entidade 2
212 A0211 Photo Weiss- Estúdio/Agência entidade coletiva 2 Photo Weiss - Estúdio/Agência
213 A0212 Museu Aero Espacial entidade coletiva 2
214 A0213 Soucasaux, Francisco pessoa 2
215 A0214 Photographia Atayama entidade coletiva 2
216 A0215 Comissão de desobstrução dos rios da Baixada Fluminense (RJ) entidade coletiva 2
217 A0216 Dias, Bastos pessoa 2
218 A0217 Costa, Osvaldo Gilson Fonseca, 1948 pessoa 2
219 A0218 Campos, Augusto César Malta de, 1864-1957 pessoa 2
220 A0219 Horacio Coppola pessoa ou entidade 2
221 A0220 Rossi, Giulio, 1824-1884 pessoa 2
222 A0221 Marcel Gautherot pessoa ou entidade 2
223 A0222 Gioconda Rizzo pessoa ou entidade 2
224 A0223 Braz pessoa ou entidade 2
225 A0224 Laurens, J pessoa 2
226 A0225 Laurens, Jules-Joseph-Augustin, 1825-1901 pessoa 2
227 A0226 Bernieri, J pessoa 2
228 A0227 Sommer, Giorgio, 1834-1914 pessoa 2
229 A0228 Pacheco & Filho pessoa ou entidade 2 PACHECO & FILHO
230 A0229 Schleier J pessoa ou entidade 2
231 A0230 Lewis, John C. A pessoa 2
232 A0231 Moreira, Archimedes pessoa 2
233 A0232 Vannini, N pessoa 2
234 A0233 Fragoso, Armando pessoa 2
235 A0234 Huberti (Fotógrafo) pessoa ou entidade 2 Huberti
236 A0235 Barboza, João de Almeida pessoa 2
237 A0236 Firpo, João pessoa 2
238 A0237 Forni, Agostino pessoa 2
239 A0238 Trebby, Frederico pessoa 2
240 A0239 Galeria Universal de Carlos Cesar pessoa ou entidade 2
241 A0240 Trebby y Cia entidade coletiva 2
242 A0241 Filgueiras, A pessoa 2
243 A0242 Sá, Gazzi de, 1901-1981 pessoa 2
244 A0243 Fernandes, Gonçalves, 1909-1986 pessoa 2
245 A0244 A. Filgueiras Photo Amador entidade coletiva 2
246 A0245 Agfa Tropex pessoa ou entidade 2
247 A0246 Aliwu pessoa ou entidade 2
248 A0247 Ultzmann, Robert, 1842-1889 pessoa 2
249 A0248 Benque, Francisco e Henschel, Alberto pessoa 2
250 A0249 Carneiro, Joaquim Feliciano Alves e Tavares pessoa 2
251 A0250 Lobo, Antônio Araújo de Souza pessoa 2
252 A0251 Oliveira, Antônio Barbosa pessoa 2
253 A0252 Pinto. J pessoa ou entidade 2
254 A0253 Ducasble, Alfredo | Fotografia Parisienne entidade coletiva 2
255 A0254 Soucasaux, Augusto pessoa 2
256 A0255 s/nome pessoa ou entidade 2
257 A0256 Photographia Popular Oliveira & Tondella entidade coletiva 2
258 A0257 Tondella, Manoel. Photografia Tondella pessoa 2
259 A0258 Du Bocage, F., F. Du Bocage Photographia entidade coletiva 2
260 A0259 Mello, Borges de, Photographia modelo Borges de Mello entidade coletiva 2
261 A0260 1º Comando do Exército entidade coletiva 2
262 A0261 Silveira, J pessoa 2
263 A0262 Guimarães, Antonio de Oliveira pessoa 2
264 A0263 Furne fils et H. Tournier pessoa ou entidade 2
265 A0264 Carneiro & Smith pessoa ou entidade 2
266 A0265 Sabino pessoa ou entidade 2
267 A0266 Arthur e J. J. Wischral pessoa ou entidade 2
268 A0267 A. C. da Costa Ribeiro pessoa ou entidade 2
269 A0268 Pittigliani, Armando pessoa 2
270 A0269 Photographia Marc Ferrez entidade coletiva 2
271 A0270 Sobrosa Rio pessoa ou entidade 1
272 A0271 Sobrosa, Antenor pessoa 1
273 A0272 José Francisco Corrêa et C pessoa ou entidade 1
274 A0273 Corrêa, José Francisco pessoa 1
275 A0274 Castro, Jorge de pessoa 1
276 A0275 Duarte, B. J. (Benedito Junqueira), 1910-1995 pessoa 1
277 A0276 Vosylius, Kazys pessoa 1
278 A0277 Leon de Rennes pessoa ou entidade 1
279 A0278 Foto aérea Campo Marinha no Galeão entidade coletiva 1
280 A0279 Lopes pessoa ou entidade 1
281 A0280 Nicola Parente pessoa ou entidade 1
282 A0281 Ferrez, Luciano (1884 - 1955) pessoa 1
283 A0282 Jean Manzon pessoa ou entidade 1
284 A0283 Valuos, Guilherme pessoa 1
285 A0284 Viggiani, N pessoa 1
286 A0285 Dutra, Olavo - Fotógrafo pessoa 1
287 A0286 Fotógrafo: Vernaut, Benjamin pessoa 1
288 A0287 Photographia Guimarães entidade coletiva 1
289 A0288 E. Av. M pessoa ou entidade 1
290 A0289 Monteiro, Augusto pessoa 1
291 A0290 Stille, Paul pessoa 1
292 A0291 cios e préTheodor pessoa ou entidade 1
293 A0292 [Otto Hees?] pessoa ou entidade 1
294 A0293 Studio Paul entidade coletiva 1
295 A0294 Dr. Menescal pessoa ou entidade 1
296 A0295 Rembrandt - Rio pessoa ou entidade 1
297 A0296 Bellati, R. (Fotógrafo) pessoa 1
298 A0297 Somlo, Tomas pessoa 1
299 A0298 Emerico pessoa ou entidade 1
300 A0299 Carlos Moskovics pessoa ou entidade 1
301 A0300 Musso, Luís, m. 1908 pessoa 1
302 A0301 Agência Nacional entidade coletiva 1
303 A0302 Walery pessoa ou entidade 1
304 A0303 Klumb, Henrique Revert pessoa 1
305 A0304 Coutinho, A pessoa 1
306 A0305 Clerget pessoa ou entidade 1
307 A0306 Adam, Victor Jean, 1801-1866 pessoa 1
308 A0307 Courtois, J pessoa 1
309 A0308 Mason, Samuel J pessoa 1
310 A0309 Bradley & Rulofson pessoa ou entidade 1
311 A0310 H. Delie and E. Bechard pessoa ou entidade 1
312 A0311 Noël, Alphonse Léon, 1807-1884 pessoa 1
313 A0312 Helios (Fotógrafo) pessoa ou entidade 1
314 A0313 Nadar, Felix, 1820-1910 pessoa 1
315 A0314 Photographia Popular entidade coletiva 1
316 A0315 Angerer, Ludwig, 1827-1879 pessoa 1
317 A0316 Schoefft, O pessoa 1
318 A0317 Mourgeon, C pessoa 1
319 A0318 Antunes, F pessoa 1
320 A0319 Aguiar, Francisco Marcellino de Souza, 1855-1935 pessoa 1
321 A0320 Marc Ferrez & Filhos pessoa ou entidade 1
322 A0321 Zaccaria, G pessoa 1
323 A0322 Photograhia Vesuvio de Nicola Maria Parente pessoa ou entidade 1
324 A0323 Silveira, Pedro Satyro de Souza da pessoa 1
325 A0324 Rocha, J. C. da pessoa 1
326 A0325 Photographia Americana de Moreira & Roltgen entidade coletiva 1
327 A0326 Moreira & Roltgen pessoa ou entidade 1
328 A0327 Lopes & Ca pessoa ou entidade 1
329 A0328 Photographia Imperial de Lopes & Ca entidade coletiva 1
330 A0329 Atelier Photograhico Hygino Soares entidade coletiva 1
331 A0330 Nunes, Henrique, 1820-1895 pessoa 1
332 A0331 Luys, Jules Bernard, 1828-1897 pessoa 1
333 A0332 Wegner & Mottu pessoa ou entidade 1
334 A0333 Brogi, Giacomo, 1822-1881 pessoa 1
335 A0334 Con, Frederico Carlos pessoa 1
336 A0335 Fenton, Roger, 1819-1869 pessoa 1
337 A0336 Banchieri, Manoel pessoa 1
338 A0337 Fratelli Alinari Fotografi pessoa ou entidade 1
339 A0338 Photographie Technique A. Fernique pessoa ou entidade 1
340 A0339 Typographia Imperial & Real de Vienna pessoa ou entidade 1
341 A0340 Clairin, Georges-Jules-Victor, 1843-1919 pessoa 1
342 A0341 Gilleta & Gilly pessoa ou entidade 1
343 A0342 Arena, Giacomo, 1818-1906 pessoa 1
344 A0343 Jerace, Francesco, 1854 - 1937 pessoa 1
345 A0344 Calzolari, Icilio pessoa 1
346 A0345 Fumeo, Pietro, 1831-1898 pessoa 1
347 A0346 Trinquart (Fotógrafo) pessoa ou entidade 1
348 A0347 Berthier, Paul, 1822-1912 pessoa 1
349 A0348 Albert, Joseph, 1825-1886 pessoa 1
350 A0349 Photographie Americaine pessoa ou entidade 1
351 A0350 Kaun Phot pessoa ou entidade 1
352 A0351 Mauritshuis (Haia, Holanda) pessoa 1
353 A0352 Salentin, Hubert, 1822-1910 pessoa 1
354 A0353 Boker, Carl, 1836-1905 pessoa 1
355 A0354 Sonderland, F, 1836-1896 pessoa 1
356 A0355 C. & A. Overbeck pessoa ou entidade 1
357 A0356 Bosch, E pessoa 1
358 A0357 Werff, Adriaen van der, 1659 - 1722 pessoa 1
359 A0358 Gleyre, Charles, 1806-1874 pessoa 1
360 A0359 Goupil & Cie pessoa ou entidade 1
361 A0360 Stacey, C.A pessoa 1
362 A0361 Draper, Henry, 1837-1882 pessoa 1
363 A0362 Ludwig, Johann Fridrich, 1670-1752 pessoa 1
364 A0363 Meireles, Vítor, 1832-1903 pessoa 1
365 A0364 José da Santíssima Trindade, Bispo, 1762-1835 pessoa 1
366 A0365 Lucarell, Mario pessoa 1
367 A0366 Costa, Heitor da Silva, 1837-1947 pessoa 1
368 A0367 Foto Lucarelli entidade coletiva 1
369 A0368 Lima, José Otávio Correia, 1878-1974 pessoa 1
370 A0369 Read, R. A pessoa 1
371 A0370 Severino (Fotógrafo) pessoa ou entidade 1
372 A0371 Hospe, Joseph pessoa 1
373 A0372 Photo Lindemann entidade coletiva 1
374 A0373 Conti, José Carlos pessoa 1
375 A0374 Photo Studio Huberti entidade coletiva 1
376 A0375 Boquel, Julien pessoa 1
377 A0376 Silva, M. Nogueira da pessoa 1
378 A0377 Hoenen, Carlos pessoa 1
379 A0378 Fábrica de Ferro de Ipanema pessoa ou entidade 1
380 A0379 Rio Branco, José Maria da Silva Paranhos, Barão do, 1845-1912 pessoa 1
381 A0380 Nickelsen (Fotógrafo) pessoa ou entidade 1
382 A0381 Lima, Antonio Mariano de, 1858-1902 pessoa 1
383 A0382 Mello, Affonso de Oliveira pessoa 1
384 A0383 Lavinthal, Joaquim Ferreira dos Santos pessoa 1
385 A0384 Photo Lavinthal entidade coletiva 1
386 A0385 Vieira, Valério, 1862-1941 pessoa 1
387 A0386 Bate & Cia entidade coletiva 1
388 A0387 Micheles (Fotógrafo) pessoa ou entidade 1
389 A0388 Rochet, Louis, 1813-1878 pessoa 1
390 A0389 Mafra, João Maximiniano pessoa 1
391 A0390 Fleury, André Augusto de Pádua, 1830-1895 pessoa 1
392 A0391 Faro, Gonçalo Paes de Azevedo, 1846-1900 pessoa 1
393 A0392 Liais, Emmanuel, 1826-1900 pessoa 1
394 A0393 Hermida Pazos, José, 1829-1921 pessoa 1
395 A0394 Aquidabã pessoa ou entidade 1
396 A0395 Oliveira, C. de pessoa 1
397 A0396 Oliveira, Candido Marinho pessoa 1
398 A0397 Satrap Photo entidade coletiva 1
399 A0398 Agfa Brovira pessoa ou entidade 1
400 A0399 Ferrez, Gilberto pessoa 1
401 A0400 Boute pessoa ou entidade 1
402 A0401 Buvelot & Prat pessoa ou entidade 1
403 A0402 Panigai, Marco di pessoa 1
404 A0403 David Latino & Franklin pessoa ou entidade 1
405 A0404 Leuthold e Dursky pessoa ou entidade 1
406 A0405 Antunes, Humberto Saraiva pessoa 1
407 A0406 Castro pessoa ou entidade 1
408 A0407 Comp. Lith. Hartmann-Reichenbach entidade coletiva 1
409 A0408 Photographia Guilherme Gaensly entidade coletiva 1
410 A0409 Papeleria Travassos pessoa ou entidade 1
411 A0410 Phototipie Marius Bar pessoa ou entidade 1
412 A0411 Bureu Poste pessoa ou entidade 1
413 A0412 Edição A. Moura pessoa ou entidade 1
414 A0413 Bureau Poste pessoa ou entidade 1
415 A0414 Ao Cantineiro Naval pessoa ou entidade 1
416 A0415 Henschel e Benque pessoa ou entidade 1
417 A0416 Mello, Marcos A. de pessoa 1
418 A0417 Soares, José Severino pessoa 1
419 A0418 Bastos, A pessoa 1
420 A0419 Henschel, Albert, 1827-1882 pessoa 1
421 A0420 Bonfioti, J pessoa 1
422 A0421 Foto Chic entidade coletiva 1
423 A0422 Barboza, Theotonio pessoa 1
424 A0423 Rogato, Guilherme pessoa 1
425 A0424 Photo Skarke entidade coletiva 1
426 A0425 Serviço Photographico de Vida Domestica entidade coletiva 1
427 A0426 Foto Studio Gloria entidade coletiva 1
428 A0427 Fotografia Alemã entidade coletiva 1
429 A0428 Brady, Mathew B., ca. 1823-1896 pessoa 1
430 A0429 Photograhia Popular Oliveira & Tondella pessoa ou entidade 1
431 A0430 Photografia Popular Oliveira & Tondella pessoa ou entidade 1
432 A0431 Manoel Tondella, Photografia Tondella pessoa 1
433 A0432 Claude Lévi-Strauss pessoa ou entidade 1
434 A0433 Monteiro,Photographie Chic Monteiro & C pessoa 1
435 A0434 Edgard Egydio de Souza pessoa ou entidade 1
436 A0435 S/A pessoa ou entidade 1
437 A0436 Chapelin E Pereira pessoa ou entidade 1
438 A0437 Poluceno & Pinho pessoa ou entidade 1
439 A0438 <ns:Co & Pinho pessoa ou entidade 1
440 A0439 Thiele & Kollien [?]; Photo Bippus Rio [?] entidade coletiva 1
441 A0440 Photographia Central entidade coletiva 1
442 A0441 Veiga, Bernardo Saturnino da pessoa 1
443 A0442 Phototypie Berthaud pessoa ou entidade 1
444 A0443 Marinho, P pessoa 1
445 A0444 A. Editora entidade coletiva 1
446 A0445 511-73, Marc pessoa 1
447 A0446 J. Stamato pessoa ou entidade 1
448 A0447 DADE pessoa ou entidade 1
449 A0448 Annunciato pessoa ou entidade 1
450 A0449 Benque pessoa ou entidade 1
451 A0450 Chapelin pessoa ou entidade 1
452 A0451 Scheidemantel, B pessoa 1
453 A0452 Photo Braz Rio entidade coletiva 1
454 A0453 Scheuenstuhl, Paulo pessoa 1
455 A0454 Caras & Caretas pessoa ou entidade 1
456 A0455 Leonar pessoa ou entidade 1
457 A0456 Azevedo, J. Faria de pessoa 1
458 A0457 Basto, F pessoa 1
File diff suppressed because it is too large Load Diff
+104
View File
@@ -0,0 +1,104 @@
instituicao categoria detentor originais n
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 3928
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional (Brasil) 1889
Museu Aeroespacial consultar o detentor Museu Aeroespacial "" 1143
Museu da Republica consultar o detentor Museu da República "" 838
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) "" 826
Museu Historico Nacional consultar o detentor Museu Histórico Nacional "" 649
Fiocruz consultar o detentor Fundação Oswaldo Cruz. Casa de Oswaldo Cruz "" 548
Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | Liberado para uso de natureza cultural 479
Diretoria do Patrimonio Historico e Documentacao da Marinha consultar o detentor Diretoria do Patrimônio Histórico e Documentação da Marinha "" 450
Arquivo Nacional consultar o detentor Arquivo Nacional (Brasil) "" 383
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "" 310
Arquivo Geral da Cidade do Rio de Janeiro consultar o detentor Arquivo Geral da Cidade do Rio de Janeiro "" 248
Leibniz-Institut fuer Laenderkunde, Leipzig requer autorização do detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 212
Fundacao Joaquim Nabuco consultar o detentor Fundação Joaquim Nabuco "" 189
Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro Em domínio público | Liberado para uso de natureza cultural 176
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Instituto Moreira Salles | Requer liberação de direitos de imagem junto ao detentor indicado no Copyright 172
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles 116
Museu Paraense Emilio Goeldi consultar o detentor Museu Paraense Emílio Goeldi "" 95
Escola de Ciencias Sociais (FGV CPDOC) consultar o detentor Fundação Getulio Vargas. Escola de Ciências Sociais (FGV CPDOC) "" 79
Museu da Republica consultar o detentor Flávio de Barros / Acervo Museu da República / Imagem recuperada digitalmente pelo Instituto Moreira Salles Flávio de Barros / Acervo Museu da República / Imagem recuperada digitalmente pelo Instituto Moreira Salles 68
Instituto Brasileiro de Geografia e Estatistica consultar o detentor Instituto Brasileiro de Geografia e Estatística "" 58
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | Liberado apenas para uso de natureza cultural 52
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Acervo Instituto Moreira Salles 27
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Solicitar imagem junto ao detentor dos direitos indicado no Copyright 19
Instituto Historico e Geografico Brasileiro consultar o detentor Instituto Histórico e Geográfico Brasileiro "" 17
Instituto Moreira Salles requer autorização do detentor Dom João de Orleans e Bragança/ Instituto Moreira Salles Dom João de Orleans e Bragança/ Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 10
Instituto Historico e Geografico Brasileiro consultar o detentor Convênio Instituto Histórico e Geográfico Brasileiro / Instituto Moreira Salles Convênio Instituto Histórico e Geográfico Brasileiro / Instituto Moreira Salles 10
Instituto Moreira Salles requer autorização do detentor Diários Associados - Rio de Janeiro/ Acervo Instituto Moreira Salles Diários Associados - Rio de Janeiro/ Acervo Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 4
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional (Brazil) 2
Instituto Moreira Salles requer autorização do detentor Flávio de Barros / Acervo Instituto Geográfico e Histórico da Bahia / Imagem recuperada digitalmente pelo Instituto Moreira Salles Flávio de Barros / Acervo Instituto Geográfico e Histórico da Bahia / Imagem recuperada digitalmente pelo Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 2
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca nacional (Brasil) 2
Instituto Moreira Salles domínio público Instituto Moreira Salles "Em domínio público | >
<ns:Fiera uso de natureza cultural" 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Instituto Moreira | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | ue>
</ns:FieldValue>
<ns:FieldValue uid=""{5094c229-4 no Copyright" 1
Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro /ns:omínio público | Liberado para uso de natureza cultural 1
Instituto Moreira Salles uso cultural liberado Instituto Moreira Salles "f1}"">Atual Túblico | Liberado para uso de natureza cultural" 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | lue>
ar imagem junto ao detentor dos direitos indicado no Copyright" 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 45c-5d93acdmagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles goryituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 7 circa</ns:Fiem junto ao detentor dos direitos indicado no Copyright 1
Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | 969b9e69c2810518cd1da941cd001da8c71cos direitos indicado no Copyright 1
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacioanl (Brasil) 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | ns:CategoryValue>FOTOGRAFIA:COLEÇÕES DO ACERVO:COLEÇcado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | DO ACERVO:COLEÇÃOjunto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | 5daf98}"">Elaborado por Grandjean de Montigny em 1827,ado no Copyright" 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles egor | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Biblioteca Nacional consultar o detentor Bilbioteca Nacional (Brasil) Bilbioteca Nacional (Brasil) 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles S:Tratuto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | s:FieldValue uid=""{48b5771a-326a-42ce-9f83-0b9c225178e4}"">
<ns:Ent" 1
Instituto Moreira Salles uso cultural liberado Instituto Moreira Salles <ns:Eio público | Liberado para uso de natureza cultural 1
Diretoria do Patrimonio Historico e Documentacao da Marinha consultar o detentor Diretoria do Patrimônio Histórico e Documentação da Marinha DPHDM 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | acbe6cdb314}"">
<nto ao detentor dos direitos indicado no Copyright" 1
Instituto Moreira Salles domínio público Instituto Moreira Salles "Em domínio público | b6979}"">sp: 13,0 x 18,0 cm</ns:ultural" 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 4bb3d1a793c4ba619352175229f38606or dos direitos indicado no Copyright 1
Instituto Moreira Salles domínio público Instituto Moreira Salles "Em domínio público | lue>
</ns:FieldValue>
<na cultural" 1
Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | ns:F 1
Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro Em domínio público | s:Fi 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | f05ea53de7866ce3bcunto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Acervo Instituto Moreira Salles | Liberado apenas para uso de natureza cultural 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 0dlicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | 7094}"">
<ns:EnumValue id=""64"">Ferrez, reitos indicado no Copyright" 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | terna</ns:CategoryValue>
<ns:CategoryValitos indicado no Copyright" 1
Museu da Republica consultar o detentor Flávio de Barros/ Álbum Canônico Virtual de Canudos/ Acervo Instituto Moreira Salles/ Copyright Museu da República Flávio de Barros/ Álbum Canônico Virtual de Canudos/ Acervo Instituto Moreira Salles/ Copyright Museu da República 1
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioeca Nacional (Brasil) 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 90d9-22fa7imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | ue>
<ns:CategoryValue>FOetentor dos direitos indicado no Copyright" 1
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles <ns:EnumValue idlles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacioinal (Brasil) 1
Biblioteca Nacional consultar o detentor Bilioteca Nacional (Brasil) Bilioteca Nacional (Brasil) 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Fiel | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | aleceu no Rio de Janeiro em 1923.</nss direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | elho</tar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro "Em domínio público | >
<ns:CategoryValue>FOTOGRAFIA:ARQU" 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles PALAVRAS-CHAVE:La Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | c679ac249ad19699ccf88058daf8075965819afe7ba6b7772b961b58119c760bd0f6c 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Pessoas</ns:CategoryVaes | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 6572455391487c6de95a8490303151ec19e40cd302bc659533d2a2949624Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 074007300000000006a00000001554368720055003a007b003900380063006pyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | b4d39078a18217be451480f38ed41348631ea3208cd4aos indicado no Copyright 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles 80stituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Biblioteca Nacional consultar o detentor Bibioteca Nacional (Brasil) Bibioteca Nacional (Brasil) 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles oryValue>FOTOGira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Leibniz-Institut fuer Laenderkunde, Leipzig requer autorização do detentor Leibniz-Institut für Länderkunde 9b3 | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles {5stituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | 109"">Ltar imagem junto ao detentor dos direitos indicado no Copyright" 1
Instituto Moreira Salles requer autorização do detentor ro em 1923.oreira Salles ro em 1923.oreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | 3db9 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | dValue>
<ns:FieldValue uid=""{8b30dbb7-97ef-4a5c-8a40-18no Copyright" 1
Instituto Moreira Salles consultar o detentor Instituto Moreira Salles "Instituto Moreira Salles | EnumValue id=""160"">nto ao detentor dos direitos indicado no Copyright" 1
1 instituicao categoria detentor originais n
2 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 3928
3 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional (Brasil) 1889
4 Museu Aeroespacial consultar o detentor Museu Aeroespacial 1143
5 Museu da Republica consultar o detentor Museu da República 838
6 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) 826
7 Museu Historico Nacional consultar o detentor Museu Histórico Nacional 649
8 Fiocruz consultar o detentor Fundação Oswaldo Cruz. Casa de Oswaldo Cruz 548
9 Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | Liberado para uso de natureza cultural 479
10 Diretoria do Patrimonio Historico e Documentacao da Marinha consultar o detentor Diretoria do Patrimônio Histórico e Documentação da Marinha 450
11 Arquivo Nacional consultar o detentor Arquivo Nacional (Brasil) 383
12 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles 310
13 Arquivo Geral da Cidade do Rio de Janeiro consultar o detentor Arquivo Geral da Cidade do Rio de Janeiro 248
14 Leibniz-Institut fuer Laenderkunde, Leipzig requer autorização do detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 212
15 Fundacao Joaquim Nabuco consultar o detentor Fundação Joaquim Nabuco 189
16 Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro Em domínio público | Liberado para uso de natureza cultural 176
17 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Instituto Moreira Salles | Requer liberação de direitos de imagem junto ao detentor indicado no Copyright 172
18 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles 116
19 Museu Paraense Emilio Goeldi consultar o detentor Museu Paraense Emílio Goeldi 95
20 Escola de Ciencias Sociais (FGV CPDOC) consultar o detentor Fundação Getulio Vargas. Escola de Ciências Sociais (FGV CPDOC) 79
21 Museu da Republica consultar o detentor Flávio de Barros / Acervo Museu da República / Imagem recuperada digitalmente pelo Instituto Moreira Salles Flávio de Barros / Acervo Museu da República / Imagem recuperada digitalmente pelo Instituto Moreira Salles 68
22 Instituto Brasileiro de Geografia e Estatistica consultar o detentor Instituto Brasileiro de Geografia e Estatística 58
23 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | Liberado apenas para uso de natureza cultural 52
24 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Acervo Instituto Moreira Salles 27
25 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Solicitar imagem junto ao detentor dos direitos indicado no Copyright 19
26 Instituto Historico e Geografico Brasileiro consultar o detentor Instituto Histórico e Geográfico Brasileiro 17
27 Instituto Moreira Salles requer autorização do detentor Dom João de Orleans e Bragança/ Instituto Moreira Salles Dom João de Orleans e Bragança/ Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 10
28 Instituto Historico e Geografico Brasileiro consultar o detentor Convênio Instituto Histórico e Geográfico Brasileiro / Instituto Moreira Salles Convênio Instituto Histórico e Geográfico Brasileiro / Instituto Moreira Salles 10
29 Instituto Moreira Salles requer autorização do detentor Diários Associados - Rio de Janeiro/ Acervo Instituto Moreira Salles Diários Associados - Rio de Janeiro/ Acervo Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 4
30 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional (Brazil) 2
31 Instituto Moreira Salles requer autorização do detentor Flávio de Barros / Acervo Instituto Geográfico e Histórico da Bahia / Imagem recuperada digitalmente pelo Instituto Moreira Salles Flávio de Barros / Acervo Instituto Geográfico e Histórico da Bahia / Imagem recuperada digitalmente pelo Instituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 2
32 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca nacional (Brasil) 2
33 Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | > <ns:Fiera uso de natureza cultural 1
34 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Instituto Moreira | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
35 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | ue> </ns:FieldValue> <ns:FieldValue uid="{5094c229-4 no Copyright 1
36 Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro /ns:omínio público | Liberado para uso de natureza cultural 1
37 Instituto Moreira Salles uso cultural liberado Instituto Moreira Salles f1}">Atual Túblico | Liberado para uso de natureza cultural 1
38 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | lue> ar imagem junto ao detentor dos direitos indicado no Copyright 1
39 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 45c-5d93acdmagem junto ao detentor dos direitos indicado no Copyright 1
40 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles goryituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
41 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 7 circa</ns:Fiem junto ao detentor dos direitos indicado no Copyright 1
42 Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | 969b9e69c2810518cd1da941cd001da8c71cos direitos indicado no Copyright 1
43 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacioanl (Brasil) 1
44 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | ns:CategoryValue>FOTOGRAFIA:COLEÇÕES DO ACERVO:COLEÇcado no Copyright 1
45 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | DO ACERVO:COLEÇÃOjunto ao detentor dos direitos indicado no Copyright 1
46 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 5daf98}">Elaborado por Grandjean de Montigny em 1827,ado no Copyright 1
47 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles egor | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
48 Biblioteca Nacional consultar o detentor Bilbioteca Nacional (Brasil) Bilbioteca Nacional (Brasil) 1
49 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles S:Tratuto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
50 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | s:FieldValue uid="{48b5771a-326a-42ce-9f83-0b9c225178e4}"> <ns:Ent 1
51 Instituto Moreira Salles uso cultural liberado Instituto Moreira Salles <ns:Eio público | Liberado para uso de natureza cultural 1
52 Diretoria do Patrimonio Historico e Documentacao da Marinha consultar o detentor Diretoria do Patrimônio Histórico e Documentação da Marinha DPHDM 1
53 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | acbe6cdb314}"> <nto ao detentor dos direitos indicado no Copyright 1
54 Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | b6979}">sp: 13,0 x 18,0 cm</ns:ultural 1
55 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 4bb3d1a793c4ba619352175229f38606or dos direitos indicado no Copyright 1
56 Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | lue> </ns:FieldValue> <na cultural 1
57 Instituto Moreira Salles domínio público Instituto Moreira Salles Em domínio público | ns:F 1
58 Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro Em domínio público | s:Fi 1
59 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | f05ea53de7866ce3bcunto ao detentor dos direitos indicado no Copyright 1
60 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Acervo Instituto Moreira Salles | Liberado apenas para uso de natureza cultural 1
61 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 0dlicitar imagem junto ao detentor dos direitos indicado no Copyright 1
62 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 7094}"> <ns:EnumValue id="64">Ferrez, reitos indicado no Copyright 1
63 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | terna</ns:CategoryValue> <ns:CategoryValitos indicado no Copyright 1
64 Museu da Republica consultar o detentor Flávio de Barros/ Álbum Canônico Virtual de Canudos/ Acervo Instituto Moreira Salles/ Copyright Museu da República Flávio de Barros/ Álbum Canônico Virtual de Canudos/ Acervo Instituto Moreira Salles/ Copyright Museu da República 1
65 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioeca Nacional (Brasil) 1
66 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 90d9-22fa7imagem junto ao detentor dos direitos indicado no Copyright 1
67 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | ue> <ns:CategoryValue>FOetentor dos direitos indicado no Copyright 1
68 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacional 1
69 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles <ns:EnumValue idlles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
70 Biblioteca Nacional consultar o detentor Biblioteca Nacional (Brasil) Biblioteca Nacioinal (Brasil) 1
71 Biblioteca Nacional consultar o detentor Bilioteca Nacional (Brasil) Bilioteca Nacional (Brasil) 1
72 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Fiel | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
73 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | aleceu no Rio de Janeiro em 1923.</nss direitos indicado no Copyright 1
74 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | elho</tar imagem junto ao detentor dos direitos indicado no Copyright 1
75 Instituto Historico e Geografico Brasileiro domínio público Instituto Histórico e Geográfico Brasileiro Em domínio público | > <ns:CategoryValue>FOTOGRAFIA:ARQU 1
76 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles PALAVRAS-CHAVE:La Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
77 Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | c679ac249ad19699ccf88058daf8075965819afe7ba6b7772b961b58119c760bd0f6c 1
78 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles Pessoas</ns:CategoryVaes | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
79 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 6572455391487c6de95a8490303151ec19e40cd302bc659533d2a2949624Copyright 1
80 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 074007300000000006a00000001554368720055003a007b003900380063006pyright 1
81 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | b4d39078a18217be451480f38ed41348631ea3208cd4aos indicado no Copyright 1
82 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles 80stituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
83 Biblioteca Nacional consultar o detentor Bibioteca Nacional (Brasil) Bibioteca Nacional (Brasil) 1
84 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles oryValue>FOTOGira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
85 Leibniz-Institut fuer Laenderkunde, Leipzig requer autorização do detentor Leibniz-Institut für Länderkunde 9b3 | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
86 Instituto Moreira Salles requer autorização do detentor Instituto Moreira Salles {5stituto Moreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
87 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | 109">Ltar imagem junto ao detentor dos direitos indicado no Copyright 1
88 Instituto Moreira Salles requer autorização do detentor ro em 1923.oreira Salles ro em 1923.oreira Salles | Solicitar imagem junto ao detentor dos direitos indicado no Copyright 1
89 Leibniz-Institut fuer Laenderkunde, Leipzig consultar o detentor Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles Convênio Leibniz-Institut fuer Laenderkunde, Leipzig/ Instituto Moreira Salles | 3db9 1
90 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | dValue> <ns:FieldValue uid="{8b30dbb7-97ef-4a5c-8a40-18no Copyright 1
91 Instituto Moreira Salles consultar o detentor Instituto Moreira Salles Instituto Moreira Salles | EnumValue id="160">nto ao detentor dos direitos indicado no Copyright 1
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+50
View File
@@ -0,0 +1,50 @@
instituicao dc_type genero especie suporte presumida n
Instituto Moreira Salles Fotografia/ Papel iconográfico fotografia papel false 2633
Biblioteca Nacional Fotografia iconográfico fotografia "" false 1852
Instituto Moreira Salles Negativo/ Vidro iconográfico negativo fotográfico vidro false 1304
Museu Aeroespacial "" iconográfico fotografia "" true 1143
Museu da Republica "" iconográfico fotografia "" true 907
Instituto Moreira Salles Diapositivo/ Vidro iconográfico diapositivo vidro false 655
Museu Historico Nacional "" iconográfico fotografia "" true 649
Fiocruz "" iconográfico fotografia "" true 548
Diretoria do Patrimonio Historico e Documentacao da Marinha "" iconográfico fotografia "" true 450
Arquivo Nacional "" iconográfico fotografia "" true 383
Biblioteca Nacional "" iconográfico fotografia "" true 371
Biblioteca Nacional Manuscrito textual manuscrito "" false 294
Instituto Moreira Salles "" iconográfico fotografia "" true 263
Arquivo Geral da Cidade do Rio de Janeiro "" iconográfico fotografia "" true 248
Leibniz-Institut fuer Laenderkunde, Leipzig Fotografia/ Papel iconográfico fotografia papel false 206
Fundacao Joaquim Nabuco "" iconográfico fotografia "" true 189
Instituto Historico e Geografico Brasileiro Fotografia/ Papel iconográfico fotografia papel false 179
Biblioteca Nacional Livro bibliográfico livro "" false 127
Instituto Moreira Salles Reprodução Fotomecânica/ Papel iconográfico reprodução fotomecânica papel false 124
Museu Paraense Emilio Goeldi "" iconográfico fotografia "" true 95
Escola de Ciencias Sociais (FGV CPDOC) "" iconográfico fotografia "" true 79
Biblioteca Nacional Gravura iconográfico gravura "" false 61
Instituto Brasileiro de Geografia e Estatistica "" iconográfico fotografia "" true 58
Instituto Moreira Salles Fotografia iconográfico fotografia "" false 55
Instituto Moreira Salles NEGATIVO/ Vidro iconográfico negativo fotográfico vidro false 50
Instituto Moreira Salles FOTOGRAFIA/ Papel iconográfico fotografia papel false 41
Instituto Historico e Geografico Brasileiro "" iconográfico fotografia "" true 27
Instituto Moreira Salles Negativo flexível iconográfico negativo fotográfico flexível false 16
Biblioteca Nacional Álbum iconográfico álbum fotográfico "" false 15
Leibniz-Institut fuer Laenderkunde, Leipzig Negativo/ Vidro iconográfico negativo fotográfico vidro false 9
Instituto Moreira Salles Outros iconográfico fotografia "" true 4
Instituto Moreira Salles NEGATIVO flexível iconográfico negativo fotográfico flexível false 4
Biblioteca Nacional Desenho iconográfico desenho "" false 3
Biblioteca Nacional Artigo de Periódico bibliográfico periódico "" false 2
Instituto Moreira Salles DIAPOSITIVO/ Vidro iconográfico diapositivo vidro false 2
Instituto Moreira Salles REPRODUÇÃO FOTOMECÂNICA/ Papel iconográfico reprodução fotomecânica papel false 1
Instituto Moreira Salles Fotografia/ Papel resinado iconográfico fotografia papel resinado false 1
Biblioteca Nacional Vista panorâmica iconográfico fotografia "" false 1
Instituto Moreira Salles da197f8b9ebf4apel iconográfico fotografia "" true 1
Instituto Moreira Salles Negativo/ Papel iconográfico negativo fotográfico papel false 1
Instituto Moreira Salles Fotografia/ Tecido iconográfico fotografia tecido false 1
Leibniz-Institut fuer Laenderkunde, Leipzig bee2e5afia/ Papel iconográfico fotografia "" true 1
Instituto Moreira Salles 481b791d7a/ Papel iconográfico fotografia "" true 1
Instituto Moreira Salles 3ceegrafia/ Papel iconográfico fotografia "" true 1
Instituto Moreira Salles """{frodução Fotomecânica/ Papel" iconográfico fotografia "" true 1
Instituto Moreira Salles 4778-rafia/ Papel iconográfico fotografia "" true 1
Instituto Moreira Salles yValue>FOa/ Papel iconográfico fotografia "" true 1
Instituto Moreira Salles 93gativo/ Vidro iconográfico fotografia "" true 1
Diretoria do Patrimonio Historico e Documentacao da Marinha Fotografia iconográfico fotografia "" false 1
1 instituicao dc_type genero especie suporte presumida n
2 Instituto Moreira Salles Fotografia/ Papel iconográfico fotografia papel false 2633
3 Biblioteca Nacional Fotografia iconográfico fotografia false 1852
4 Instituto Moreira Salles Negativo/ Vidro iconográfico negativo fotográfico vidro false 1304
5 Museu Aeroespacial iconográfico fotografia true 1143
6 Museu da Republica iconográfico fotografia true 907
7 Instituto Moreira Salles Diapositivo/ Vidro iconográfico diapositivo vidro false 655
8 Museu Historico Nacional iconográfico fotografia true 649
9 Fiocruz iconográfico fotografia true 548
10 Diretoria do Patrimonio Historico e Documentacao da Marinha iconográfico fotografia true 450
11 Arquivo Nacional iconográfico fotografia true 383
12 Biblioteca Nacional iconográfico fotografia true 371
13 Biblioteca Nacional Manuscrito textual manuscrito false 294
14 Instituto Moreira Salles iconográfico fotografia true 263
15 Arquivo Geral da Cidade do Rio de Janeiro iconográfico fotografia true 248
16 Leibniz-Institut fuer Laenderkunde, Leipzig Fotografia/ Papel iconográfico fotografia papel false 206
17 Fundacao Joaquim Nabuco iconográfico fotografia true 189
18 Instituto Historico e Geografico Brasileiro Fotografia/ Papel iconográfico fotografia papel false 179
19 Biblioteca Nacional Livro bibliográfico livro false 127
20 Instituto Moreira Salles Reprodução Fotomecânica/ Papel iconográfico reprodução fotomecânica papel false 124
21 Museu Paraense Emilio Goeldi iconográfico fotografia true 95
22 Escola de Ciencias Sociais (FGV CPDOC) iconográfico fotografia true 79
23 Biblioteca Nacional Gravura iconográfico gravura false 61
24 Instituto Brasileiro de Geografia e Estatistica iconográfico fotografia true 58
25 Instituto Moreira Salles Fotografia iconográfico fotografia false 55
26 Instituto Moreira Salles NEGATIVO/ Vidro iconográfico negativo fotográfico vidro false 50
27 Instituto Moreira Salles FOTOGRAFIA/ Papel iconográfico fotografia papel false 41
28 Instituto Historico e Geografico Brasileiro iconográfico fotografia true 27
29 Instituto Moreira Salles Negativo flexível iconográfico negativo fotográfico flexível false 16
30 Biblioteca Nacional Álbum iconográfico álbum fotográfico false 15
31 Leibniz-Institut fuer Laenderkunde, Leipzig Negativo/ Vidro iconográfico negativo fotográfico vidro false 9
32 Instituto Moreira Salles Outros iconográfico fotografia true 4
33 Instituto Moreira Salles NEGATIVO flexível iconográfico negativo fotográfico flexível false 4
34 Biblioteca Nacional Desenho iconográfico desenho false 3
35 Biblioteca Nacional Artigo de Periódico bibliográfico periódico false 2
36 Instituto Moreira Salles DIAPOSITIVO/ Vidro iconográfico diapositivo vidro false 2
37 Instituto Moreira Salles REPRODUÇÃO FOTOMECÂNICA/ Papel iconográfico reprodução fotomecânica papel false 1
38 Instituto Moreira Salles Fotografia/ Papel resinado iconográfico fotografia papel resinado false 1
39 Biblioteca Nacional Vista panorâmica iconográfico fotografia false 1
40 Instituto Moreira Salles da197f8b9ebf4apel iconográfico fotografia true 1
41 Instituto Moreira Salles Negativo/ Papel iconográfico negativo fotográfico papel false 1
42 Instituto Moreira Salles Fotografia/ Tecido iconográfico fotografia tecido false 1
43 Leibniz-Institut fuer Laenderkunde, Leipzig bee2e5afia/ Papel iconográfico fotografia true 1
44 Instituto Moreira Salles 481b791d7a/ Papel iconográfico fotografia true 1
45 Instituto Moreira Salles 3ceegrafia/ Papel iconográfico fotografia true 1
46 Instituto Moreira Salles "{frodução Fotomecânica/ Papel iconográfico fotografia true 1
47 Instituto Moreira Salles 4778-rafia/ Papel iconográfico fotografia true 1
48 Instituto Moreira Salles yValue>FOa/ Papel iconográfico fotografia true 1
49 Instituto Moreira Salles 93gativo/ Vidro iconográfico fotografia true 1
50 Diretoria do Patrimonio Historico e Documentacao da Marinha Fotografia iconográfico fotografia false 1
+6
View File
@@ -0,0 +1,6 @@
# Nível 0 — acervo da entidade custodiadora
## 3.1 Âmbito e conteúdo
Cópias digitais de acervos fotográficos brasileiros, mantidas para preservação
e consulta. Hoje, uma coleção: a Brasiliana Fotográfica (BR RJXYZ.BF).
+136
View File
@@ -0,0 +1,136 @@
# Nível 1 — Coleção Brasiliana Fotográfica (cópia digital)
Cada seção `## N.N` preenche o elemento de mesmo número da NOBRADE no nível 1.
Lido por `pipeline/nobrade/montar.py`. Seções vazias são ignoradas.
## 2.2 História administrativa/Biografia
Coleção formada em setembro de 2026 para preservar uma cópia integral da
Brasiliana Fotográfica, portal criado em 2015 pela Biblioteca Nacional e pelo
Instituto Moreira Salles para reunir, num único repositório DSpace, acervos
fotográficos dos séculos XIX e XX de instituições brasileiras e estrangeiras.
O eixo temático é o do próprio portal: a fotografia produzida no Brasil ou
sobre o Brasil.
## 2.3 História arquivística
Natureza da acumulação: coleção. Reunida intencionalmente por cópia digital,
sem transferência de custódia dos originais, que permanecem nas 15
instituições de origem (5.1 de cada dossiê).
A Biblioteca Nacional foi consultada antes da coleta. Confirmou que o material
é público e que não tinha equipe técnica para fornecer um dump; a coleta por
raspagem, em ritmo cortês e com identificação, foi o caminho combinado.
Intervenções técnicas, em ordem:
1. Metadados (setembro de 2026): 13.060 itens enumerados pelo índice de
navegação ao vivo do DSpace (`browse?type=title`), comunidade a comunidade.
O sitemap oficial, gerado em abril de 2019, lista só cerca de 41% do acervo
e foi descartado como fonte. O registro completo de cada item
(`?show=full`) foi colhido a partir de um navegador real, porque o
Cloudflare do site bloqueia automação.
2. Arquivos: para cada item foi guardado o bitstream do DSpace como imagem de
preservação (maior resolução disponível; digitalizações de até 34,7 MB), a
miniatura gerada pelo DSpace e, quando existia, a cópia legada do
objdigital.bn.br, de resolução bem menor, guardada como procedência. 115
itens tinham de 2 a 6 imagens reais, e todas foram guardadas (nível 5).
3. Cada arquivo foi baixado, somado (SHA-256), enviado ao bucket e apagado do
disco local. O ledger do envio é a fonte dos elementos 5.2 e 1.5 de cada
dossiê.
4. Coleta concluída em 13 de setembro de 2026.
Sinistros e dispersões: 69 itens não têm imagem de preservação porque a origem
responde HTTP 500 ao bitstream, embora a página do item responda 200. Foram
feitas três rodadas de tentativa. Nesses itens a cópia guarda só a miniatura
(ver 6.1 de cada um e `errors.md`). Arquivos que chegaram corrompidos ou que
eram pirâmides de blocos (DZI) em vez de imagem foram rejeitados pelo ledger e
refeitos.
## 2.4 Procedência
Brasiliana Fotográfica (https://brasilianafotografica.bn.gov.br/), repositório
DSpace 4.2 mantido pela Biblioteca Nacional, handles `20.500.12156.1/*`. Cópia
obtida por raspagem combinada com a Biblioteca Nacional, 9–13 de setembro de 2026.
Inclui também os 636 posts do blog editorial do portal, usados em 5.4 e nas
fontes das autoridades.
## 3.2 Avaliação, eliminação e temporalidade
Nenhum item foi eliminado: a coleção é uma cópia integral. Entre as versões de
um mesmo arquivo foi mantida a de maior resolução (preservação), e a cópia
legada do objdigital foi guardada como procedência, nunca como substituta.
Arquivos rejeitados na validação (corrompidos, em formato de blocos, ou de
licença em vez de imagem) foram descartados e registrados no ledger.
## 3.3 Incorporações
Não há incorporações previstas. Uma nova coleta completa pode ser feita se a
origem publicar itens novos; o `fetched_at` de cada dossiê permite comparar.
## 3.4 Sistema de arranjo
Arranjo em quatro níveis abaixo da coleção:
- seção (nível 2): instituição de origem, conforme a comunidade do DSpace;
- série (nível 3): coleção ou fundo de origem, normalizado a partir de
`dc.source`. Itens sem coleção identificável ficam na série AV (Avulsos) da
seção;
- dossiê (nível 4): um item do DSpace, identificado pelo número do handle;
- item documental (nível 5): cada imagem do dossiê, numerada `01`, `02`…
Código de referência: `BR RJXYZ.BF.<seção>.<série>.<handle>.<imagem>`.
## 4.2 Condições de reprodução
Cada dossiê traz em 4.2 a condição informada pela origem (domínio público, uso
cultural liberado, reprodução sujeita a autorização, ou não informada) e o
detentor dos direitos. As instituições têm políticas distintas: a decisão de
reproduzir é item a item, junto ao detentor indicado.
## 4.3 Idioma
Descrições em português. Há legendas e títulos originais em francês, inglês,
latim, alemão, italiano, ucraniano e húngaro, registrados em 4.3 de cada
dossiê (ISO 639-2).
## 4.4 Características físicas e requisitos técnicos
Arquivos digitais JPEG (com alguns PNG e PDF), abertos em qualquer visualizador
de imagem. Os maiores passam de 8.000 px no lado maior. Nenhum requisito
especial.
## 4.5 Instrumentos de pesquisa
- Mural 3D navegável com busca e filtros: https://xn--2dk.xyz/brasiliana/
- Esta descrição em EAD 3: `descricao/ead/brasiliana.xml` (no bucket, em
`s3://brasiliana/descricao/`).
- Catálogo bruto em Dublin Core: `s3://brasiliana/catalogo.jsonl`.
## 5.1 Existência e localização dos originais
Os originais pertencem às 15 instituições de origem, listadas como seções. Cada
dossiê indica a instituição, o endereço do item na Brasiliana Fotográfica e,
quando a origem publica, o código ou a notação da instituição.
## 6.2 Notas gerais
Os valores dos metadados de origem que foram normalizados (datas, direitos,
nomes) estão preservados em 6.2 de cada dossiê e no `catalogo.jsonl`. Valores
visivelmente corrompidos na origem, com fragmentos de XML ou hash no lugar do
texto, foram desconsiderados e anotados.
## 7.1 Nota do arquivista
Descrição gerada automaticamente a partir dos metadados Dublin Core colhidos,
por `pipeline/nobrade`, com tabelas de revisão em `descricao/revisao/`.
Fontes: registros `?show=full` do DSpace, ledger de envio do bucket, blog da
Brasiliana Fotográfica. Responsável: rafapolo.
## 8.1 Pontos de acesso e indexação de assuntos
Pontos de acesso: título (1.2), autores em forma autorizada ISAAR(CPF)
(`descricao/autoridades.jsonl`, com as variantes como remissivas), data
tópica e lugares (`dc.coverage`), assuntos (`dc.subject`, com os termos em
português separados das traduções inglesas) e período (ISO 8601-2). Os
assuntos seguem o vocabulário da origem, sem controle adicional nesta versão.
+7
View File
@@ -0,0 +1,7 @@
# Seção AGCRJ
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Arquivo público do município do Rio de Janeiro. O conjunto inclui a Coleção Augusto Malta, fotógrafo oficial da prefeitura no início do século XX.
+7
View File
@@ -0,0 +1,7 @@
# Seção AN
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Arquivo Nacional, Rio de Janeiro, órgão central do Sistema de Gestão de Documentos de Arquivo da administração pública federal, criado em 1838.
+7
View File
@@ -0,0 +1,7 @@
# Seção BN
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Biblioteca nacional do Brasil, com origem na Real Biblioteca trazida de Portugal em 1810, no Rio de Janeiro. Mantém a Brasiliana Fotográfica. A maior parte do seu conjunto aqui vem da Coleção Thereza Christina Maria, doada por D. Pedro II.
+7
View File
@@ -0,0 +1,7 @@
# Seção COC
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Casa de Oswaldo Cruz, unidade da Fundação Oswaldo Cruz dedicada à memória e à história das ciências e da saúde. O conjunto vem de fundos institucionais e pessoais ligados à saúde pública.
+7
View File
@@ -0,0 +1,7 @@
# Seção CPDOC
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Centro de Pesquisa e Documentação de História Contemporânea do Brasil, da Fundação Getulio Vargas, Rio de Janeiro, criado em 1973. Guarda arquivos pessoais de figuras da vida pública brasileira.
+7
View File
@@ -0,0 +1,7 @@
# Seção DPHDM
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Órgão da Marinha do Brasil responsável pelo patrimônio histórico e documental naval. O conjunto é formado sobretudo por álbuns fotográficos de viagens, escolas de aprendizes marinheiros e aviação naval.
+7
View File
@@ -0,0 +1,7 @@
# Seção FUNDAJ
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Fundação Joaquim Nabuco, instituição federal de pesquisa sediada no Recife. O conjunto documenta sobretudo Pernambuco e o Nordeste.
+7
View File
@@ -0,0 +1,7 @@
# Seção IBGE
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Instituto Brasileiro de Geografia e Estatística. O conjunto documenta municípios brasileiros, trabalhos geográficos de campo e eventos institucionais.
+7
View File
@@ -0,0 +1,7 @@
# Seção IFL
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Leibniz-Institut für Länderkunde, instituto de pesquisa em geografia regional em Leipzig, Alemanha. Participa da Brasiliana Fotográfica por convênio com o Instituto Moreira Salles.
+7
View File
@@ -0,0 +1,7 @@
# Seção IHGB
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Instituto Histórico e Geográfico Brasileiro, fundado em 1838 no Rio de Janeiro. Participa da Brasiliana Fotográfica por convênio com o Instituto Moreira Salles.
+7
View File
@@ -0,0 +1,7 @@
# Seção IMS
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Instituição cultural privada criada em 1992, no Rio de Janeiro, pela família Moreira Salles. Seu acervo fotográfico, com coleções como Gilberto Ferrez, Mestres do Século XIX e Pedro Corrêa do Lago, é o maior conjunto da Brasiliana Fotográfica, da qual é parceira fundadora com a Biblioteca Nacional.
+7
View File
@@ -0,0 +1,7 @@
# Seção MHN
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Museu Histórico Nacional, Rio de Janeiro, criado em 1922. O conjunto inclui as coleções Miguel Calmon e Juan Gutierrez.
+7
View File
@@ -0,0 +1,7 @@
# Seção MPEG
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Museu Paraense Emílio Goeldi, instituição de pesquisa sediada em Belém, dedicada ao estudo da Amazônia.
+7
View File
@@ -0,0 +1,7 @@
# Seção MR
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Museu instalado no Palácio do Catete, Rio de Janeiro, antiga sede da Presidência da República. O conjunto inclui as coleções Família Passos, Getúlio Vargas, Nilo Peçanha e as fotografias de Flávio de Barros sobre Canudos.
+7
View File
@@ -0,0 +1,7 @@
# Seção MUSAL
Rascunho — conferir antes de publicar.
## 2.2 História administrativa
Museu da Força Aérea Brasileira, no Campo dos Afonsos, Rio de Janeiro. O conjunto reúne sobretudo fotografias aéreas e de aviação militar das décadas de 1920 e 1930.
+6
View File
@@ -0,0 +1,6 @@
# Textos das séries (nível 3)
Um arquivo `<SEÇÃO>.<SÉRIE>.md` (ex.: `IMS.GF.md`) com seções `## 2.2`,
`## 3.1` ou `## 3.4` substitui o texto gerado para aquela série. Sem arquivo,
o 3.1 é o resumo automático: quantidade, datas-limite, principais autores e
lugares. Os códigos das séries estão em `../revisao/series.tsv`.
View File
+53
View File
@@ -0,0 +1,53 @@
"""python -m nobrade (de dentro de pipeline/)
Gera a descrição NOBRADE completa em descricao/: unidades, autoridades,
tabelas de revisão, pendências, EAD 3, EAC-CPF e CSV do AtoM, e valida os XML
contra os XSD de nobrade/xsd/ quando o xmllint está disponível.
"""
import shutil
import subprocess
import sys
from collections import defaultdict
from pathlib import Path
from . import exporta, montar, valida
from .config import SAIDA
def main():
print('montando unidades…', flush=True)
unidades, aut = montar.monta()
lista = sorted(unidades.values(), key=lambda u: (u['nivel'], u['id']))
lista = [{k: v for k, v in u.items() if not k.startswith('_') and v is not None} for u in lista]
pend = valida.valida(lista)
print(f'{len(lista)} unidades, {len(aut.registros)} autoridades, {pend} pendências obrigatórias')
print('exportando EAD 3, EAC-CPF e AtoM…', flush=True)
exporta.ead(lista, aut.registros)
usos = defaultdict(list)
for u in lista:
if u['nivel'] == 4:
for p in u['2.1']:
if p.get('id'):
usos[p['id']].append(u['id'])
exporta.eac(list(aut.registros.values()), usos)
exporta.atom(lista)
if shutil.which('xmllint') and '--sem-xsd' not in sys.argv:
xsd = Path(__file__).parent / 'xsd'
r = subprocess.run(['xmllint', '--noout', '--huge', '--schema', xsd / 'ead3.xsd',
SAIDA / 'ead' / 'brasiliana.xml'], capture_output=True, text=True)
print('EAD 3:', (r.stderr.strip().splitlines() or ['?'])[-1])
eacs = sorted((SAIDA / 'eac').glob('*.xml'))
r = subprocess.run(['xmllint', '--noout', '--schema', xsd / 'cpf.xsd', *eacs],
capture_output=True, text=True)
falhas = [x for x in r.stderr.splitlines() if 'fails to validate' in x or 'error' in x.lower()]
print(f'EAC-CPF: {len(eacs)} arquivos, {len(falhas)} com erro')
for x in falhas[:10]:
print(' ', x)
return 1 if pend else 0
if __name__ == '__main__':
sys.exit(main())
+119
View File
@@ -0,0 +1,119 @@
"""Registros de autoridade (ISAAR(CPF)) para produtores — elemento 2.1 e 8.1.
Junta as grafias de `dc.contributor` ("Malta, Augusto", "Malta, Augusto,
1864-1957", "Marc Ferrez" e "Ferrez, Marc") numa forma autorizada, com as
variantes como remissivas (proc. 8.1.4).
"""
from __future__ import annotations
import re
import unicodedata
from collections import Counter, defaultdict
ANONIMO = re.compile(r'(?i)^\s*(an[oô]nimo|autoria n[aã]o identificada|s/\s*autor|sem autor|desconhecid[oa]|'
r'n[aã]o identificad[oa]|autor n[aã]o identificado|autor desconhecido)\s*\.?$')
COLETIVA = re.compile(r'(?i)\b(escola|officina|oficina|photographia|fotografia|photo|foto|studio|est[uú]dio|atelier|'
r'casa|companhia|cia\.?|museu|instituto|minist[eé]rio|servi[cç]o|diretoria|departamento|'
r'comiss[aã]o|biblioteca|arquivo|editora|lith|litografia|tipografia|typ|&|irm[aã]os|'
r'sociedade|empresa|jornal|revista|ag[eê]ncia|governo|prefeitura|marinha|ex[eé]rcito|'
r'for[cç]a|aeron[aá]utica|avia[cç][aã]o|universidade|fundação)\b')
DATAS = re.compile(r',?\s*((?:ca\.\s*|fl\.\s*|m\.\s*|n\.\s*)?\d{4}\??(?:\s*-\s*(?:ca\.\s*)?\d{0,4}\??)?)\.?\s*$')
PARTICULAS = {'de', 'da', 'do', 'das', 'dos', 'e', 'von', 'van', 'du', 'del', 'di'}
def _chave(s: str) -> str:
s = ''.join(c for c in unicodedata.normalize('NFD', s.lower()) if unicodedata.category(c) != 'Mn')
s = re.sub(r'\(.*?\)', '', s)
return re.sub(r'[^\w,]+', ' ', s).strip(' ,')
def _separa_datas(nome: str) -> tuple[str, str | None]:
nome = nome.strip().rstrip('.')
if m := DATAS.search(nome):
if ',' in nome[:m.start()] or m[1].startswith(('fl', 'm.', 'n.', 'ca')):
return nome[:m.start()].strip(' ,'), m[1]
return nome, None
def _inverte(nome: str) -> str | None:
"""'Marc Ferrez' → 'Ferrez, Marc'. Só para nomes de pessoa sem vírgula."""
partes = nome.split()
if len(partes) < 2 or ',' in nome:
return None
i = len(partes) - 1
while i > 1 and partes[i - 1].lower() in PARTICULAS:
i -= 1
return f"{' '.join(partes[i:])}, {' '.join(partes[:i])}"
def periodo(datas: str | None) -> tuple[int, int] | None:
"""Anos prováveis de atividade: fl. A-B, ou nascimento+15 até a morte."""
if not datas:
return None
anos = [int(a) for a in re.findall(r'\d{4}', datas)]
if not anos:
return None
if datas.startswith('fl'):
return (anos[0], anos[-1]) if len(anos) > 1 else (anos[0], anos[0])
if datas.startswith('m.'):
return None
if len(anos) == 2:
return anos[0] + 15, anos[1]
return None
class Autoridades:
def __init__(self):
self.contagem: Counter = Counter()
def registra(self, nome: str):
if nome and nome.strip() and not ANONIMO.match(nome):
self.contagem[nome.strip()] += 1
def resolve(self):
"""Agrupa as grafias. Depois disso `forma(nome)` devolve o id da autoridade."""
grupos: dict[str, Counter] = defaultdict(Counter)
for nome, n in self.contagem.items():
base, _ = _separa_datas(nome)
grupos[_chave(base)][nome] += n
# grafias diretas ("Marc Ferrez") que batem com uma invertida já conhecida
for k in list(grupos):
if ',' in k:
continue
nome = next(iter(grupos[k]))
if COLETIVA.search(nome):
continue
inv = _inverte(_separa_datas(nome)[0])
if inv and _chave(inv) in grupos and _chave(inv) != k:
grupos[_chave(inv)].update(grupos.pop(k))
self.registros: dict[str, dict] = {}
self._id_de: dict[str, str] = {}
for k, variantes in sorted(grupos.items(), key=lambda kv: -sum(kv[1].values())):
# forma autorizada: a variante mais completa (com datas) e mais usada
# (datas com início e fim > só uma data > nenhuma), depois frequência
def peso(v):
dt = _separa_datas(v)[1] or ''
return (len(re.findall(r'\d{4}', dt)), variantes[v], v)
forma = max(variantes, key=peso)
forma = forma.strip().rstrip('.')
base, datas = _separa_datas(forma)
tipo = 'entidade coletiva' if COLETIVA.search(base) else ('pessoa' if ',' in base else 'pessoa ou entidade')
if re.match(r'(?i)fam[ií]lia\b', base):
tipo = 'família'
aid = 'A' + str(len(self.registros) + 1).zfill(4)
self.registros[aid] = {
'id': aid, 'forma_autorizada': forma, 'nome': base, 'datas_existencia': datas,
'tipo': tipo, 'variantes': sorted(v for v in variantes if v.strip().rstrip('.') != forma),
'ocorrencias': sum(variantes.values()), 'periodo_atividade': periodo(datas),
'fontes': [],
}
for v in variantes:
self._id_de[v] = aid
def id(self, nome: str) -> str | None:
return self._id_de.get((nome or '').strip())
def __getitem__(self, aid: str) -> dict:
return self.registros[aid]
+177
View File
@@ -0,0 +1,177 @@
"""Normalizadores de campo único: espécie/suporte (1.5), características
físicas (1.5/4.4), direitos (4.2), idioma (4.3), lugar (1.3.1 data tópica) e
assuntos (8.1)."""
from __future__ import annotations
import re
import unicodedata
CORROMPIDO = re.compile(r'[<>{}]|ns:|PALAVRAS-CHAVE|^[0-9a-f]{6,}|\d[a-f]\d[a-f]\d')
def sem_acento(s: str) -> str:
return ''.join(c for c in unicodedata.normalize('NFD', s) if unicodedata.category(c) != 'Mn')
def corrompido(v: str | None) -> bool:
return bool(v) and bool(CORROMPIDO.search(v))
# ── 1.5 espécie e suporte (a partir de dc.type) ─────────────────────────────
ESPECIES = [ # (padrão, gênero, espécie)
(r'^negativo', 'iconográfico', 'negativo fotográfico'),
(r'^diapositivo', 'iconográfico', 'diapositivo'),
(r'reprodu[cç][aã]o fotomec', 'iconográfico', 'reprodução fotomecânica'),
(r'^(fotografia|vista panor)', 'iconográfico', 'fotografia'),
(r'^gravura', 'iconográfico', 'gravura'),
(r'^desenho', 'iconográfico', 'desenho'),
(r'^[áa]lbum', 'iconográfico', 'álbum fotográfico'),
(r'^manuscrito', 'textual', 'manuscrito'),
(r'^livro', 'bibliográfico', 'livro'),
(r'^artigo de peri', 'bibliográfico', 'periódico'),
]
def especie(tipo: str | None) -> dict:
"""{'genero', 'especie', 'suporte', 'presumida'}. Sem dc.type (ou com lixo),
presume fotografia — o acervo inteiro é um repositório fotográfico — e marca."""
t = (tipo or '').strip()
if t and not corrompido(t):
base, _, sup = t.partition('/')
b = sem_acento(base.strip().lower())
for pat, gen, esp in ESPECIES:
if re.search(pat, b) or re.search(pat, base.strip().lower()):
suporte = sup.strip().lower() or None
if esp == 'negativo fotográfico' and 'flex' in b:
suporte = 'flexível'
return {'genero': gen, 'especie': esp, 'suporte': suporte, 'presumida': False}
return {'genero': 'iconográfico', 'especie': 'fotografia', 'suporte': None, 'presumida': True,
'original': t or None}
# ── características físicas que algumas instituições põem em dc.description ──
FISICO = re.compile(
r'(?i)^\s*(p\s*&\s*b|p/b|preto e branco|cor(ida)?|colorid[ao]|s[ée]pia|'
r'albumina|gelatina|prata|col[oó]dio|cianotipia|platina|carv[aã]o|ambr[oó]tipo|daguerre[oó]tipo|'
r'negativo|acetato|nitrato|vidro|papel|cart[aã]o|\d+[,.]?\d*\s*x\s*\d+|processo:|segunda gera)')
def e_fisico(v: str) -> bool:
return bool(FISICO.match(v)) and len(v) < 120
def cor(fisico: list[str]) -> str | None:
t = ' '.join(fisico).lower()
if re.search(r'p\s*&\s*b|p/b|preto e branco', t):
return 'p&b'
if re.search(r'colorid|\bcor\b', t):
return 'cor'
return None
# ── 4.2 condições de reprodução ─────────────────────────────────────────────
def direitos(textos: list[str], instituicao: str) -> dict:
"""{'categoria', 'detentor', 'texto', 'originais'}."""
limpos = list(dict.fromkeys(t.strip() for t in textos if t and t.strip() and t.strip() != 'None'))
junto = sem_acento(' '.join(limpos).lower())
if re.search(r'dominio publico|omínio público|omi?nio publico', junto):
cat = 'domínio público'
elif 'liberado para uso de natureza cultural' in junto:
cat = 'uso cultural liberado'
elif re.search(r'solicitar|requer libera', junto):
cat = 'requer autorização do detentor'
else:
cat = 'consultar o detentor'
detentor = None
for t in limpos:
a = sem_acento(t.lower())
if corrompido(t) or re.search(r'dominio publico|solicitar|requer|liberado', a) or len(t) < 6:
continue
if 'bibli' in a and 'nac' in a:
detentor = 'Biblioteca Nacional (Brasil)'
elif 'moreira' in a and 'salles' in a and '/' not in t:
detentor = 'Instituto Moreira Salles'
else:
detentor = t
break
detentor = detentor or instituicao
frases = {
'domínio público': 'Imagem em domínio público.',
'uso cultural liberado': 'Uso liberado para fins de natureza cultural.',
'requer autorização do detentor': 'Reprodução sujeita a autorização do detentor dos direitos.',
'consultar o detentor': 'Condições de reprodução não informadas na origem; consultar o detentor.',
}
return {'categoria': cat, 'detentor': detentor,
'texto': f'{frases[cat]} Detentor indicado: {detentor}.',
'originais': limpos or None}
# ── 4.3 idioma ───────────────────────────────────────────────────────────────
NOMES_IDIOMA = {'por': 'português', 'fre': 'francês', 'eng': 'inglês', 'lat': 'latim', 'ger': 'alemão',
'ita': 'italiano', 'ukr': 'ucraniano', 'hun': 'húngaro', 'spa': 'espanhol'}
def idiomas(vs: list[str]) -> list[dict]:
out = []
for v in vs:
c = (v or '').strip().lower()
if c in NOMES_IDIOMA and c not in [o['codigo'] for o in out]:
out.append({'codigo': c, 'nome': NOMES_IDIOMA[c]})
return out
# ── 1.3.1 data tópica e 8.1 lugares ─────────────────────────────────────────
UF = {'AC', 'AL', 'AP', 'AM', 'BA', 'CE', 'DF', 'ES', 'GO', 'MA', 'MT', 'MS', 'MG', 'PA', 'PB', 'PR', 'PE',
'PI', 'RJ', 'RN', 'RS', 'RO', 'RR', 'SC', 'SP', 'SE', 'TO'}
ESTADOS = {'rio de janeiro': 'RJ', 'sao paulo': 'SP', 'bahia': 'BA', 'pernambuco': 'PE', 'minas gerais': 'MG',
'para': 'PA', 'amazonas': 'AM', 'parana': 'PR', 'rio grande do sul': 'RS', 'santa catarina': 'SC',
'ceara': 'CE', 'maranhao': 'MA', 'espirito santo': 'ES', 'goias': 'GO', 'mato grosso': 'MT',
'paraiba': 'PB', 'alagoas': 'AL', 'sergipe': 'SE', 'piaui': 'PI', 'rio grande do norte': 'RN'}
PAISES = {'brasil', 'brazil'}
def lugar(coberturas: list[str]) -> str | None:
"""A forma mais específica de cidade: 'Cidade (UF)'. Junta 'Rio de Janeiro' + 'RJ'."""
cs = [c.strip() for c in coberturas if c and c.strip() and not corrompido(c)]
for c in cs:
if m := re.fullmatch(r'(.+?)\s*(?:\(|,\s*|\s-\s*)([A-Z]{2})\)?', c):
if m[2] in UF and sem_acento(m[1].lower()) not in PAISES:
return f'{m[1].strip()} ({m[2]})'
ufs = [c for c in cs if c in UF]
for c in cs:
k = sem_acento(c.lower())
if k in PAISES or c in UF or '(estado)' in k or 'state' in k:
continue
if re.search(r'\(([^)]+)\)$', c): # "Paris (França)", "Rio de Janeiro (Brazil)"
nome, pais = re.match(r'(.+?)\s*\(([^)]+)\)$', c).groups()
if sem_acento(pais.lower()) in PAISES:
uf = ESTADOS.get(sem_acento(nome.lower()))
return f'{nome} ({uf})' if uf else nome
return c
uf = ufs[0] if ufs else ESTADOS.get(k)
return f'{c} ({uf})' if uf else c
return None
# ── 8.1 assuntos: separa as traduções inglesas que o DSpace da BN repete ─────
EN = {'the', 'and', 'of', 'in', 'on', 'women', 'men', 'children', 'streets', 'street', 'buildings', 'building',
'churches', 'church', 'views', 'view', 'slaves', 'railroads', 'railroad', 'harbors', 'harbor', 'landscapes',
'portraits', 'bridges', 'rivers', 'houses', 'squares', 'parks', 'gardens', 'mountains', 'beaches',
'ships', 'soldiers', 'history', 'photographs', 'people', 'indians', 'coffee', 'workers', 'palaces',
'monuments', 'waterfalls', 'boats', 'plantations', 'aerial', 'military', 'city', 'cities', 'public',
'social', 'life', 'customs', 'description', 'travel', 'transportation', 'agriculture', 'industry',
'architecture', 'fountains', 'hospitals', 'schools', 'markets', 'lakes', 'bays', 'islands', 'forts',
'wars', 'war', 'emperors', 'kings', 'queens', 'nobility', 'family', 'families', 'politicians'}
PT = {'de', 'da', 'do', 'das', 'dos', 'e', 'em', 'no', 'na', 'nos', 'nas', 'para', 'com'}
def idioma_termo(t: str) -> str:
if re.search(r'[ãõçáéíóúâêô]', t.lower()):
return 'por'
palavras = set(re.findall(r'[a-z]+', t.lower()))
if palavras & PT:
return 'por'
if palavras & EN or re.search(r'\((?:brazil|state)', t.lower()):
return 'eng'
return 'por'
+72
View File
@@ -0,0 +1,72 @@
"""Constantes da descrição NOBRADE — decisões registradas em CONARQ.md §5."""
from pathlib import Path
RAIZ = Path(__file__).resolve().parents[2]
PIPELINE = RAIZ / 'pipeline'
CATALOGO = PIPELINE / 'catalogo.jsonl'
LEDGER = PIPELINE / 'subidor.sqlite'
POSTS = PIPELINE / 'wordpress-posts.jsonl'
ERROS = RAIZ / 'errors.md'
AJUSTES = Path(__file__).resolve().parent / 'ajustes'
SAIDA = RAIZ / 'descricao'
TEXTOS = SAIDA / 'textos'
REVISAO = SAIDA / 'revisao'
# 1.1 — código da entidade custodiadora. PROVISÓRIO até o CONARQ atribuir um
# (proc. 1.1.1). Trocar aqui regenera todos os códigos de referência.
# Formato do CODEARQ, como o AGCRJ usa: país, espaço, UF + sigla, e as partes
# da unidade separadas por ponto — BR RJAGCRJ.SOP.NL.AVE.03.01
PAIS = 'BR'
ENTIDADE = 'RJXYZ'
ENTIDADE_NOME = 'xyz — cópia digital de acervos fotográficos'
ENTIDADE_SITE = 'https://xn--2dk.xyz/brasiliana/'
COLECAO = 'BF'
COLECAO_TITULO = 'Coleção Brasiliana Fotográfica (cópia digital)'
RESPONSAVEL = 'rafapolo'
BUCKET = 's3://brasiliana'
REGRAS = ('NOBRADE: Norma brasileira de descrição arquivística (CONARQ, 2006); '
'ISAD(G) 2ª ed. (CIA, 2000); ISAAR(CPF) 2ª ed. (CIA, 2004); '
'datas em ISO 8601-2 (EDTF); idiomas em ISO 639-2; países em ISO 3166.')
ORIGEM_NOME = 'Brasiliana Fotográfica'
ORIGEM_SITE = 'https://brasilianafotografica.bn.gov.br/'
HANDLE_URL = 'https://brasilianafotografica.bn.gov.br/brasiliana/handle/{}'
# Nível 2 — uma seção por instituição de origem (campo `community` do catálogo).
# sigla → (nome autorizado, cidade)
INSTITUICOES = {
'Instituto Moreira Salles': ('IMS', 'Instituto Moreira Salles', 'Rio de Janeiro (RJ)'),
'Biblioteca Nacional': ('BN', 'Biblioteca Nacional (Brasil)', 'Rio de Janeiro (RJ)'),
'Museu Aeroespacial': ('MUSAL', 'Museu Aeroespacial', 'Rio de Janeiro (RJ)'),
'Museu da Republica': ('MR', 'Museu da República', 'Rio de Janeiro (RJ)'),
'Museu Historico Nacional': ('MHN', 'Museu Histórico Nacional', 'Rio de Janeiro (RJ)'),
'Fiocruz': ('COC', 'Fundação Oswaldo Cruz. Casa de Oswaldo Cruz', 'Rio de Janeiro (RJ)'),
'Diretoria do Patrimonio Historico e Documentacao da Marinha':
('DPHDM', 'Diretoria do Patrimônio Histórico e Documentação da Marinha', 'Rio de Janeiro (RJ)'),
'Arquivo Nacional': ('AN', 'Arquivo Nacional (Brasil)', 'Rio de Janeiro (RJ)'),
'Arquivo Geral da Cidade do Rio de Janeiro':
('AGCRJ', 'Arquivo Geral da Cidade do Rio de Janeiro', 'Rio de Janeiro (RJ)'),
'Leibniz-Institut fuer Laenderkunde, Leipzig':
('IFL', 'Leibniz-Institut für Länderkunde', 'Leipzig (Alemanha)'),
'Instituto Historico e Geografico Brasileiro':
('IHGB', 'Instituto Histórico e Geográfico Brasileiro', 'Rio de Janeiro (RJ)'),
'Fundacao Joaquim Nabuco': ('FUNDAJ', 'Fundação Joaquim Nabuco', 'Recife (PE)'),
'Museu Paraense Emilio Goeldi': ('MPEG', 'Museu Paraense Emílio Goeldi', 'Belém (PA)'),
'Escola de Ciencias Sociais (FGV CPDOC)':
('CPDOC', 'Fundação Getulio Vargas. Escola de Ciências Sociais (FGV CPDOC)', 'Rio de Janeiro (RJ)'),
'Instituto Brasileiro de Geografia e Estatistica':
('IBGE', 'Instituto Brasileiro de Geografia e Estatística', 'Rio de Janeiro (RJ)'),
}
# 4.1 — obrigatório nos níveis 0 e 1
ACESSO = ('Sem restrição de acesso à descrição. As cópias digitais são mantidas '
f'para preservação em {BUCKET} e consultáveis pelo mural em {ENTIDADE_SITE}. '
'O acesso aos originais segue as regras de cada instituição de origem '
'(ver 5.1 em cada dossiê).')
def codigo(*partes: str) -> str:
"""BR RJXYZ, BR RJXYZ.BF, BR RJXYZ.BF.IMS.GF.12345.01 …"""
return f'{PAIS} ' + '.'.join((ENTIDADE,) + tuple(p for p in partes if p))
+333
View File
@@ -0,0 +1,333 @@
"""Normalização de dc.date para o elemento 1.3 da NOBRADE.
Saída de `interpreta(texto)`:
forma — como a NOBRADE manda exibir: `1914`, `[1860]`, `[1902?]`,
`[ca. 1905]`, `[193-]`, `[18--?]`, `8/2/1890-18/4/1890`
iso — ISO 8601-2 (EDTF), para indexação e intercâmbio (proc. 1.3.2.7):
`1914`, `1902?`, `1905~`, `193X`, `18XX?`, `1931/1937`, `../1921`
inicio, fim — anos inteiros (ou None) para filtrar e ordenar
qualidade — `exata` | `atribuida` | `incerta` | `aproximada`
tipo — `produção` (padrão) ou `publicação`
motivo — quando não deu para interpretar: `sem data`, `registro de sistema`,
`ilegível`
A regra geral: tira do texto as marcas (colchetes, `?`, `circa`, qualificadores
entre parênteses), interpreta o que sobra como ponto ou intervalo e remonta a
forma com as marcas no padrão da norma (proc. 1.3.2.1–1.3.2.4).
"""
from __future__ import annotations
import re
import unicodedata
from dataclasses import dataclass, field
MESES = {
'jan': 1, 'janeiro': 1, 'fev': 2, 'fevereiro': 2, 'mar': 3, 'março': 3, 'marco': 3,
'abr': 4, 'abril': 4, 'mai': 5, 'maio': 5, 'jun': 6, 'junho': 6,
'jul': 7, 'julho': 7, 'ago': 8, 'agosto': 8, 'set': 9, 'setembro': 9,
'out': 10, 'outubro': 10, 'nov': 11, 'novembro': 11, 'dez': 12, 'dezembro': 12,
}
MES_RE = '(' + '|'.join(sorted(MESES, key=len, reverse=True)) + r')\.?'
SEM_DATA = re.compile(r'^(s\.?\s*/?\s*d\.?|s/data|sem data|s\.?\s*n\.?|n[aã]o identificad[ao])$', re.I)
@dataclass
class Ponto:
ano: int
mes: int | None = None
dia: int | None = None
prec: str = 'ano' # dia | mes | ano | decada | seculo
def forma(self) -> str:
if self.prec == 'dia':
return f'{self.dia}/{self.mes}/{self.ano}'
if self.prec == 'mes':
return f'{self.mes}/{self.ano}'
if self.prec == 'decada':
return f'{self.ano // 10}-'
if self.prec == 'seculo':
return f'{self.ano // 100}--'
return str(self.ano)
def iso(self) -> str:
if self.prec == 'dia':
return f'{self.ano:04d}-{self.mes:02d}-{self.dia:02d}'
if self.prec == 'mes':
return f'{self.ano:04d}-{self.mes:02d}'
if self.prec == 'decada':
return f'{self.ano // 10}X'
if self.prec == 'seculo':
return f'{self.ano // 100}XX'
return f'{self.ano:04d}'
def limites(self) -> tuple[int, int]:
if self.prec == 'decada':
return self.ano, self.ano + 9
if self.prec == 'seculo':
return self.ano, self.ano + 99
return self.ano, self.ano
@dataclass
class Data:
original: str
inicio_p: Ponto | None = None
fim_p: Ponto | None = None
relacao: str = '' # '' | 'antes' | 'depois'
colchete: bool = False
incerta: bool = False
aproximada: bool = False
tipo: str = 'produção'
motivo: str = ''
notas: list[str] = field(default_factory=list)
@property
def ok(self) -> bool:
return self.inicio_p is not None
@property
def qualidade(self) -> str:
if self.aproximada:
return 'aproximada'
if self.incerta:
return 'incerta'
if self.colchete:
return 'atribuida'
return 'exata'
def forma(self) -> str:
if not self.ok:
return '[s.d.]'
a = self.inicio_p.forma()
if self.relacao == 'antes':
s = f'antes de {a}'
elif self.relacao == 'depois':
s = f'depois de {a}'
elif self.fim_p and self.fim_p != self.inicio_p:
s = f'{a}-{self.fim_p.forma()}'
else:
s = a
if self.aproximada:
s = 'ca. ' + s
if self.incerta:
s += '?'
if self.colchete or self.aproximada or self.incerta or self.relacao:
s = f'[{s}]'
return s
def iso(self) -> str | None:
if not self.ok:
return None
q = ('%' if self.incerta else '~') if self.aproximada else ('?' if self.incerta else '')
a = self.inicio_p.iso() + q
if self.relacao == 'antes':
return f'../{a}'
if self.relacao == 'depois':
return f'{a}/..'
if self.fim_p and self.fim_p != self.inicio_p:
return f'{a}/{self.fim_p.iso()}{q}'
return a
def anos(self) -> tuple[int | None, int | None]:
if not self.ok:
return None, None
i, f = self.inicio_p.limites()
if self.fim_p:
f = self.fim_p.limites()[1]
if self.relacao == 'antes':
return None, f
if self.relacao == 'depois':
return i, None
return i, f
def registro(self) -> dict:
i, f = self.anos()
return {
'original': self.original, 'forma': self.forma(), 'iso': self.iso(),
'inicio': i, 'fim': f, 'qualidade': self.qualidade if self.ok else None,
'tipo': self.tipo, 'motivo': self.motivo or None,
'notas': self.notas or None,
}
def _sem_acento(s: str) -> str:
return ''.join(c for c in unicodedata.normalize('NFD', s) if unicodedata.category(c) != 'Mn')
def _ano(s: str, base: int | None = None) -> int:
n = int(s)
if len(s) == 2:
return (base // 100 * 100 if base else 1900) + n
return n
def _ponto(s: str) -> tuple[Ponto | None, bool]:
"""Um ponto no tempo. Devolve (ponto, incerto) — incerto quando o próprio
formato carrega a dúvida, como `193?` (década) ou `?/08/1938` (dia)."""
s = s.strip(' .,:;')
s = re.sub(r'^[-–]\s*', '', s)
if not s:
return None, False
if m := re.fullmatch(r'(\d{4})', s):
return Ponto(int(m[1])), False
if m := re.fullmatch(r'(\d{3})-', s):
return Ponto(int(m[1]) * 10, prec='decada'), False
if m := re.fullmatch(r'(\d{3})-?\?', s):
return Ponto(int(m[1]) * 10, prec='decada'), True
if m := re.fullmatch(r'(\d{2})(?:-{2,3}|_)', s):
return Ponto(int(m[1]) * 100, prec='seculo'), False
if m := re.fullmatch(r'(\d{2})(?:-{2})?\?', s):
return Ponto(int(m[1]) * 100, prec='seculo'), True
if m := re.fullmatch(r'(\d{3})--', s): # [186--]: década escrita com traço a mais
return Ponto(int(m[1]) * 10, prec='decada'), False
# dia/mês/ano, com separadores tortos: 22-12--1938, 14 -07-1928, 05/12-1934
if m := re.fullmatch(r'(\d{1,2})\s*[-/.]\s*(\d{1,2})\s*[-/.]+\s*(\d{4}|\d{2})', s):
d, mo, a = int(m[1]), int(m[2]), _ano(m[3])
if 1 <= mo <= 12 and 1 <= d <= 31:
return Ponto(a, mo, d, 'dia'), len(m[3]) == 2
if m := re.fullmatch(r'(\d{4})\s*[-/]\s*(\d{1,2})\s*[-/]\s*(\d{1,2})', s):
a, mo, d = int(m[1]), int(m[2]), int(m[3])
if 1 <= mo <= 12 and 1 <= d <= 31:
return Ponto(a, mo, d, 'dia'), False
# dia desconhecido: 2-/12/1923, ?/08/1938
if m := re.fullmatch(r'(?:\d?-|\?)\s*/\s*(\d{1,2})\s*/\s*(\d{4})', s):
return Ponto(int(m[2]), int(m[1]), prec='mes'), False
if m := re.fullmatch(r'(\d{1,2})\s*/\s*(\d{4})', s):
if 1 <= int(m[1]) <= 12:
return Ponto(int(m[2]), int(m[1]), prec='mes'), False
if m := re.fullmatch(r'(\d{4})\s*/\s*(\d{1,2})', s):
if 1 <= int(m[2]) <= 12:
return Ponto(int(m[1]), int(m[2]), prec='mes'), False
t = _sem_acento(s.lower())
if m := re.fullmatch(rf'(\d{{1,2}})\s*(?:de\s+)?{MES_RE}\s*,?\s*(?:de\s+)?(\d{{4}})', t):
return Ponto(int(m[3]), MESES[m[2]], int(m[1]), 'dia'), False
if m := re.fullmatch(rf'{MES_RE}\s*,?\s*(?:de\s+)?(\d{{4}})', t):
return Ponto(int(m[2]), MESES[m[1]], prec='mes'), False
if m := re.fullmatch(r'(?:decada de )?(\d{3})\d(?: decada)?( provavel)?', t):
if 'decada' in t:
return Ponto(int(m[1]) * 10, prec='decada'), bool(m[2])
if m := re.fullmatch(r'(\d{2}) seculo', t):
return Ponto((int(m[1]) - 1) * 100, prec='seculo'), False
return None, False
def _intervalo(s: str) -> tuple[Ponto | None, Ponto | None, bool]:
t = _sem_acento(s.lower()).strip(' .,:;')
t = re.sub(r'^entre\s+', '', t)
p, inc = _ponto(t)
if p:
return p, None, inc
# dias ou meses coordenados: "15 e 16 de outubro de 1930", "outubro e novembro de 1930"
if m := re.fullmatch(rf'(\d{{1,2}})\s+e\s+(\d{{1,2}})\s+(?:de\s+)?{MES_RE}\s+(?:de\s+)?(\d{{4}})', t):
mo, a = MESES[m[3]], int(m[4])
return Ponto(a, mo, int(m[1]), 'dia'), Ponto(a, mo, int(m[2]), 'dia'), False
if m := re.fullmatch(rf'{MES_RE}\s+e\s+{MES_RE}\s+(?:de\s+)?(\d{{4}})', t):
a = int(m[3])
return Ponto(a, MESES[m[1]], prec='mes'), Ponto(a, MESES[m[2]], prec='mes'), False
# 1859-61: segundo ano abreviado
if m := re.fullmatch(r'(\d{4})\s*-\s*(\d{2})', t):
a = int(m[1])
b = _ano(m[2], a)
if b > a:
return Ponto(a), Ponto(b), False
# o traço separa só entre um ano e o início do outro — `193-` é década, não intervalo
for sep in (r'\s+e\s+', r'\s+a\s+', r'(?<=[\d?])\s*[-–]\s*(?=\d)', r'\s*/\s*'):
partes = re.split(sep, t)
if len(partes) != 2:
continue
# "/" só separa anos inteiros (1952/1953); com meses é data (1910/12)
if sep == r'\s*/\s*' and not all(re.fullmatch(r'\d{4}', p) for p in partes):
continue
a, ia = _ponto(partes[0])
b, ib = _ponto(partes[1])
if a and b and b.limites()[1] >= a.limites()[0]:
return a, b, ia or ib
return None, None, False
def interpreta(texto: str | None) -> Data:
original = (texto or '').strip()
d = Data(original)
s = original
if not s:
d.motivo = 'sem data'
return d
if re.fullmatch(r'\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}Z', s):
# carimbo de registro no DSpace gravado no campo errado — não é produção
d.motivo = 'registro de sistema'
d.notas.append(f'dc.date traz a data de registro no sistema de origem ({s}), não a de produção')
return d
# partes separadas por ";" com qualificador: fica a de produção, o resto vira nota
partes = [p.strip() for p in re.split(r';(?![^(]*\))', s) if p.strip()]
if len(partes) > 1:
principal = next((p for p in partes if re.search(r'produ', p, re.I)), partes[0])
d.notas += [f'dc.date também registra: {p}' for p in partes if p is not principal]
s = principal
if m := re.search(r'\(([^)]*)\)\s*$', s):
q = m[1].lower()
if 'publica' in q:
d.tipo = 'publicação'
if 'atribu' in q:
d.colchete = True
s = s[:m.start()].strip()
if re.search(r'[\[\]{]', s):
d.colchete = True
s = re.sub(r'[\[\]{}]', '', s)
s = re.sub(r'^\s*-\s*', '', s)
s = re.sub(r'^(RJ|[A-Z]{2}),\s*', '', s) # [RJ, ca. 1860]: lugar vai na data tópica
s = re.sub(r'(\d)\.(\d{3})\b', r'\1\2', s) # 1.885 → 1885
s = re.sub(r'\s*:?\.\s*$', '', s).strip()
if SEM_DATA.fullmatch(s):
d.motivo = 'sem data'
return d
s, n = re.subn(r'\b(circa|cica|cira|ca\.?|c\.)\s*|(?<=\[)c(?=\d)|^c(?=\d)', '', s, flags=re.I)
if n:
d.aproximada = True
s, n = re.subn(r'\s*\b(anterior|antes de)\b\s*', ' ', s, flags=re.I)
if n:
d.relacao = 'antes'
s, n = re.subn(r'\s*\b(posterior|depois de)\b\s*', ' ', s, flags=re.I)
if n:
d.relacao = 'depois'
s = s.strip()
# interrogação no fim vale para a data inteira; dentro de um ponto (193?) é o ponto que diz
if re.search(r'\d{4}\s*\?\s*$', s) or re.search(r'\d{4}\?\s*\]?$', original):
d.incerta = True
s = re.sub(r'\s*\?\s*$', '', s)
# "Foto aérea da Fábrica ... - SP - 23-06-1933": só a data do fim interessa
if not re.match(r'[\d?]', s) and not re.match(rf'(?i){MES_RE}|entre|decada|década', _sem_acento(s)):
if m := re.search(r'(\d{1,2}-\d{1,2}-\d{4}|\d{4})\s*$', s):
d.notas.append(f'data extraída do texto: {original}')
s = m[1]
p, inc = _ponto(s)
if p:
d.inicio_p, d.incerta = p, d.incerta or inc
return d
a, b, inc = _intervalo(s)
if a:
d.inicio_p, d.fim_p, d.incerta = a, b, d.incerta or inc
return d
# "1900-" (colchete aberto): dali em diante
if m := re.fullmatch(r'(\d{4})\s*-', s):
d.inicio_p, d.relacao = Ponto(int(m[1])), 'depois'
return d
d.motivo = 'ilegível'
return d
def atribuida(inicio: int, fim: int, base: str) -> dict:
"""Data atribuída pelo arquivista a partir de outra fonte (proc. 1.3.3.2)."""
d = Data('', Ponto(inicio), Ponto(fim) if fim != inicio else None, incerta=True, colchete=True)
r = d.registro()
r['original'] = None
r['notas'] = [f'data atribuída pelo arquivista: {base}']
return r
+352
View File
@@ -0,0 +1,352 @@
"""Exportação da descrição: EAD 3 (descrições), EAC-CPF (autoridades) e CSV
de importação do AtoM (modelo ISAD). A NOBRADE não impõe formato; recomenda o
EAD para intercâmbio (nota 13).
Correspondência NOBRADE → EAD 3:
1.1 unitid · 1.2 unittitle · 1.3 unitdate (@normal em ISO 8601-2) ·
1.4 @level · 1.5 physdesc + physdescstructured · 2.1 origination ·
2.2 bioghist · 2.3 custodhist · 2.4 acqinfo · 3.1 scopecontent ·
3.2 appraisal · 3.3 accruals · 3.4 arrangement · 4.1 accessrestrict ·
4.2 userestrict · 4.3 langmaterial · 4.4 phystech · 4.5 otherfindaid ·
5.1 originalsloc · 5.2 altformavail + dao · 5.3 relatedmaterial ·
5.4 bibliography · 6.1 odd[@localtype=conservacao] · 6.2 odd ·
7.1 processinfo · 7.2 control/conventiondeclaration · 7.3 control/maintenancehistory ·
8.1 controlaccess
"""
from __future__ import annotations
import csv
import re
import xml.etree.ElementTree as ET
from collections import defaultdict
from datetime import date
from .config import ENTIDADE, ENTIDADE_NOME, PAIS, REGRAS, SAIDA
EAD = 'http://ead3.archivists.org/schema/'
CPF = 'urn:isbn:1-931666-33-4'
XLINK = 'http://www.w3.org/1999/xlink'
NIVEL_EAD = {1: ('collection', None), 2: ('otherlevel', 'seção'), 3: ('series', None),
4: ('file', None), 5: ('item', None)}
HOJE = date.today().isoformat()
# ── texto plano de cada elemento (usado por EAD, AtoM e mural) ──────────────
def texto(u: dict, el: str) -> str | None:
v = u.get(el)
if v is None:
return None
if el == '1.2':
return v['titulo']
if el == '1.3':
p = v.get('producao') or {}
return p.get('forma')
if el == '1.5':
return v.get('texto')
if el == '2.1':
return '; '.join(p['forma'] for p in v)
if el == '4.2':
return v['texto'] if isinstance(v, dict) else v
if el == '4.3':
return '; '.join(i['nome'] for i in v) if isinstance(v, list) else v
if el == '5.1':
return v.get('texto') or v.get('instituicao') if isinstance(v, dict) else v
if el == '5.2':
if isinstance(v, str):
return v
partes = [f"{c['tipo']}: {c['chave']} (SHA-256 {c['sha256']})" for c in v.get('nesta_entidade') or []]
partes += [f"{c['entidade']}: {c['url']}" for c in v.get('em_outras_entidades') or []]
return '; '.join(partes) or None
if el in ('5.3', '5.4', '6.2') and isinstance(v, list):
return '\n'.join(v)
if el == '7.3':
return '; '.join(f'{k}: {x}' for k, x in v.items())
if el == '8.1' and isinstance(v, dict):
return None
return v if isinstance(v, str) else None
# ── EAD 3 ────────────────────────────────────────────────────────────────────
def _sub(pai, tag, txt=None, **attrs):
e = ET.SubElement(pai, f'{{{EAD}}}{tag}', {k.rstrip('_'): str(x) for k, x in attrs.items() if x is not None})
if txt is not None:
e.text = txt
return e
def _paragrafos(pai, tag, txt, head=None, **attrs):
if not txt:
return
e = _sub(pai, tag, **attrs)
if head:
_sub(e, 'head', head)
for par in [p.strip() for p in re.split(r'\n\s*\n|\n(?=[-\d])', txt) if p.strip()]:
_sub(e, 'p', re.sub(r'\s+', ' ', par))
def _nome(pai, forma: str, aid: str | None, tipo: str | None, relator=None):
tag = {'entidade coletiva': 'corpname', 'família': 'famname'}.get(tipo, 'persname')
e = _sub(pai, tag, identifier=aid, relator=relator)
_sub(e, 'part', forma)
return e
def _componente(pai, u: dict, aut: dict, tag='c'):
nivel, outro = NIVEL_EAD[u['nivel']]
c = pai if tag == 'archdesc' else _sub(pai, 'c', level=nivel, otherlevel=outro, id=_xmlid(u['id']))
did = _sub(c, 'did')
_sub(did, 'unitid', u['1.1'], countrycode=PAIS, repositorycode=f'{PAIS}-{ENTIDADE}')
_sub(did, 'unittitle', u['1.2']['titulo'])
p = u['1.3'].get('producao') or {}
cert = {'aproximada': 'approximate', 'incerta': 'uncertain', 'atribuida': 'inferred',
'atribuída pelo arquivista': 'inferred'}.get(p.get('qualidade'))
_sub(did, 'unitdate', p.get('forma') or '[s.d.]', normal=p.get('iso'),
datechar='publication' if p.get('tipo') == 'publicação' else 'creation', certainty=cert,
unitdatetype='inclusive' if u['nivel'] < 4 else None)
orig = _sub(did, 'origination')
for pr in u['2.1']:
_nome(orig, pr['forma'], pr.get('id'), (aut.get(pr.get('id')) or {}).get('tipo'),
relator=pr.get('funcao'))
dim = u['1.5']
_sub(did, 'physdesc', dim['texto'])
for esp, n in (dim.get('por_especie') or {}).items():
ps = _sub(did, 'physdescstructured', physdescstructuredtype='materialtype', coverage='part')
_sub(ps, 'quantity', str(n))
_sub(ps, 'unittype', esp)
if isinstance(u.get('4.3'), list):
lm = _sub(did, 'langmaterial')
for i in u['4.3']:
_sub(lm, 'language', i['nome'], langcode=i['codigo'])
if u['nivel'] == 5:
for cp in (u.get('5.2') or {}).get('nesta_entidade') or []:
_sub(did, 'dao', daotype='derived', href=cp['chave'], linktitle=cp['tipo'],
identifier=f"sha256:{cp['sha256']}")
_paragrafos(c, 'bioghist', u.get('2.2'))
_paragrafos(c, 'custodhist', u.get('2.3'))
_paragrafos(c, 'acqinfo', u.get('2.4'))
_paragrafos(c, 'scopecontent', u.get('3.1'))
_paragrafos(c, 'appraisal', u.get('3.2'))
_paragrafos(c, 'accruals', u.get('3.3'))
_paragrafos(c, 'arrangement', u.get('3.4'))
_paragrafos(c, 'accessrestrict', u.get('4.1'))
_paragrafos(c, 'userestrict', texto(u, '4.2'))
_paragrafos(c, 'phystech', u.get('4.4'))
_paragrafos(c, 'otherfindaid', u.get('4.5'))
_paragrafos(c, 'originalsloc', texto(u, '5.1'))
if u['nivel'] != 5:
_paragrafos(c, 'altformavail', texto(u, '5.2'))
if isinstance(u.get('5.3'), list):
rm = _sub(c, 'relatedmaterial')
for x in u['5.3']:
_sub(rm, 'p', x)
if isinstance(u.get('5.4'), list):
bib = _sub(c, 'bibliography')
for x in u['5.4']:
_sub(bib, 'bibref', x)
elif u.get('5.4'):
_paragrafos(c, 'bibliography', u['5.4'])
_paragrafos(c, 'odd', u.get('6.1'), head='Notas sobre conservação', localtype='conservacao')
_paragrafos(c, 'odd', texto(u, '6.2'), head='Notas gerais')
_paragrafos(c, 'processinfo', u.get('7.1'))
ca = u.get('8.1')
if isinstance(ca, dict):
ctl = _sub(c, 'controlaccess')
for s in ca.get('assuntos') or []:
_sub(_sub(ctl, 'subject', lang='por'), 'part', s)
for s in ca.get('assuntos_eng') or []:
_sub(_sub(ctl, 'subject', lang='eng'), 'part', s)
if u['1.3'].get('topica'):
_sub(_sub(ctl, 'geogname', localtype='data tópica'), 'part', u['1.3']['topica'])
for s in ca.get('lugares') or []:
_sub(_sub(ctl, 'geogname'), 'part', s)
for pr in u['2.1']:
if pr.get('id'):
_nome(ctl, pr['forma'], pr['id'], (aut.get(pr['id']) or {}).get('tipo'))
if len(ctl) == 0:
c.remove(ctl)
elif ca:
_paragrafos(c, 'processinfo', ca, head='Pontos de acesso e indexação')
return c
def _xmlid(cod: str) -> str:
return 'u-' + re.sub(r'[^\w.-]', '_', cod)
def ead(unidades: list[dict], aut: dict):
filhos = defaultdict(list)
por_id = {}
for u in unidades:
por_id[u['id']] = u
if u.get('pai'):
filhos[u['pai']].append(u['id'])
col = next(u for u in unidades if u['nivel'] == 1)
ET.register_namespace('', EAD)
raiz = ET.Element(f'{{{EAD}}}ead')
ctrl = _sub(raiz, 'control', langencoding='iso639-2b', scriptencoding='iso15924',
dateencoding='iso8601', countryencoding='iso3166-1', repositoryencoding='iso15511')
_sub(ctrl, 'recordid', col['id'])
fd = _sub(ctrl, 'filedesc')
ts = _sub(fd, 'titlestmt')
_sub(ts, 'titleproper', col['1.2']['titulo'])
_sub(ctrl, 'maintenancestatus', value='new')
ag = _sub(ctrl, 'maintenanceagency', countrycode=PAIS)
_sub(ag, 'agencycode', f'{PAIS}-{ENTIDADE}')
_sub(ag, 'agencyname', ENTIDADE_NOME)
ld = _sub(ctrl, 'languagedeclaration')
_sub(ld, 'language', 'português', langcode='por')
_sub(ld, 'script', 'latino', scriptcode='Latn')
cd = _sub(ctrl, 'conventiondeclaration')
_sub(cd, 'citation', REGRAS)
mh = _sub(ctrl, 'maintenancehistory')
ev = _sub(mh, 'maintenanceevent')
_sub(ev, 'eventtype', value='created')
_sub(ev, 'eventdatetime', HOJE, standarddatetime=HOJE)
_sub(ev, 'agenttype', value='machine')
_sub(ev, 'agent', 'pipeline/nobrade')
arch = _sub(raiz, 'archdesc', level='collection')
_componente(arch, col, aut, tag='archdesc')
rep = arch.find(f'{{{EAD}}}did')
r = _sub(rep, 'repository')
_sub(_sub(r, 'corpname', identifier=f'{PAIS}-{ENTIDADE}'), 'part', ENTIDADE_NOME)
dsc = _sub(arch, 'dsc')
def desce(pai_xml, cod):
for fid in sorted(filhos[cod], key=lambda x: (len(x), x)):
c = _componente(pai_xml, por_id[fid], aut)
desce(c, fid)
desce(dsc, col['id'])
(SAIDA / 'ead').mkdir(exist_ok=True)
ET.indent(raiz, space=' ')
ET.ElementTree(raiz).write(SAIDA / 'ead' / 'brasiliana.xml', encoding='utf-8', xml_declaration=True)
# ── EAC-CPF ──────────────────────────────────────────────────────────────────
def _c(pai, tag, txt=None, **attrs):
e = ET.SubElement(pai, f'{{{CPF}}}{tag}', {k.rstrip('_'): str(x) for k, x in attrs.items() if x is not None})
if txt is not None:
e.text = txt
return e
def eac(autoridades: list[dict], usos: dict[str, list[str]]):
ET.register_namespace('', CPF)
ET.register_namespace('xlink', XLINK)
pasta = SAIDA / 'eac'
pasta.mkdir(exist_ok=True)
for a in autoridades:
raiz = ET.Element(f'{{{CPF}}}eac-cpf')
ctrl = _c(raiz, 'control')
_c(ctrl, 'recordId', f"{PAIS}-{ENTIDADE}-{a['id']}")
_c(ctrl, 'maintenanceStatus', 'new')
ag = _c(ctrl, 'maintenanceAgency')
_c(ag, 'agencyCode', f'{PAIS}-{ENTIDADE}')
_c(ag, 'agencyName', ENTIDADE_NOME)
ld = _c(ctrl, 'languageDeclaration')
_c(ld, 'language', 'português', languageCode='por')
_c(ld, 'script', 'latino', scriptCode='Latn')
cd = _c(ctrl, 'conventionDeclaration')
_c(cd, 'citation', 'ISAAR(CPF) 2ª ed.; NOBRADE (CONARQ, 2006), proc. 8.1.3–8.1.4')
mh = _c(ctrl, 'maintenanceHistory')
ev = _c(mh, 'maintenanceEvent')
_c(ev, 'eventType', 'created')
_c(ev, 'eventDateTime', HOJE, standardDateTime=HOJE)
_c(ev, 'agentType', 'machine')
_c(ev, 'agent', 'pipeline/nobrade')
if a['fontes']:
src = _c(ctrl, 'sources')
for f in a['fontes']:
s = _c(src, 'source')
_c(s, 'sourceEntry', f)
cpf = _c(raiz, 'cpfDescription')
ident = _c(cpf, 'identity')
_c(ident, 'entityType', {'entidade coletiva': 'corporateBody', 'família': 'family'}.get(a['tipo'], 'person'))
ne = _c(ident, 'nameEntry', localType='autorizada')
_c(ne, 'part', a['nome'])
if a['datas_existencia']:
_c(ne, 'useDates').append(_data_eac(a['datas_existencia']))
_c(ne, 'authorizedForm', 'NOBRADE')
for v in a['variantes']:
nv = _c(ident, 'nameEntry', localType='variante')
_c(nv, 'part', v)
_c(nv, 'alternativeForm', 'NOBRADE')
desc = _c(cpf, 'description')
if a['datas_existencia']:
ex = _c(desc, 'existDates')
ex.append(_data_eac(a['datas_existencia']))
bh = _c(desc, 'biogHist')
_c(bh, 'p', f"Autor de {a['ocorrencias']} dossiês da Coleção Brasiliana Fotográfica (cópia digital)."
+ (f" Tipo presumido: {a['tipo']}." if a['tipo'] == 'pessoa ou entidade' else ''))
if usos.get(a['id']):
rel = _c(cpf, 'relations')
for cod in usos[a['id']][:500]:
r = _c(rel, 'resourceRelation', resourceRelationType='creatorOf')
_c(r, 'relationEntry', cod)
ET.indent(raiz, space=' ')
ET.ElementTree(raiz).write(pasta / f"{a['id']}.xml", encoding='utf-8', xml_declaration=True)
def _data_eac(datas: str):
anos = re.findall(r'\d{4}', datas)
if len(anos) >= 2:
e = ET.Element(f'{{{CPF}}}dateRange')
_c(e, 'fromDate', datas.split('-')[0].strip(), standardDate=anos[0])
_c(e, 'toDate', datas.split('-')[-1].strip(), standardDate=anos[1])
return e
e = ET.Element(f'{{{CPF}}}date', standardDate=anos[0] if anos else None)
e.text = datas
return e
# ── AtoM (modelo CSV ISAD da versão 2.x) ────────────────────────────────────
ATOM = ['legacyId', 'parentId', 'identifier', 'title', 'levelOfDescription', 'extentAndMedium',
'repository', 'archivalHistory', 'acquisition', 'scopeAndContent', 'appraisal', 'accruals',
'arrangement', 'accessConditions', 'reproductionConditions', 'language', 'physicalCharacteristics',
'findingAids', 'locationOfOriginals', 'locationOfCopies', 'relatedUnitsOfDescription',
'publicationNote', 'generalNote', 'subjectAccessPoints', 'placeAccessPoints', 'nameAccessPoints',
'descriptionIdentifier', 'rules', 'archivistNote', 'eventDates', 'eventTypes', 'eventStartDates',
'eventEndDates', 'eventActors', 'culture']
NIVEL_ATOM = {1: 'Coleção', 2: 'Seção', 3: 'Série', 4: 'Dossiê', 5: 'Item documental'}
def atom(unidades: list[dict]):
with (SAIDA / 'atom.csv').open('w', encoding='utf-8', newline='') as f:
w = csv.DictWriter(f, fieldnames=ATOM)
w.writeheader()
for u in unidades:
if u['nivel'] == 0:
continue
p = u['1.3'].get('producao') or {}
ca = u.get('8.1') if isinstance(u.get('8.1'), dict) else {}
w.writerow({
'legacyId': u['id'], 'parentId': u['pai'] if u['nivel'] > 1 else '',
'identifier': u['1.1'].split('.')[-1] if u['nivel'] > 1 else u['1.1'],
'title': u['1.2']['titulo'], 'levelOfDescription': NIVEL_ATOM[u['nivel']],
'extentAndMedium': texto(u, '1.5'), 'repository': ENTIDADE_NOME,
'archivalHistory': u.get('2.3'), 'acquisition': u.get('2.4'),
'scopeAndContent': u.get('3.1'), 'appraisal': u.get('3.2'), 'accruals': u.get('3.3'),
'arrangement': u.get('3.4'), 'accessConditions': u.get('4.1'),
'reproductionConditions': texto(u, '4.2'),
'language': '|'.join(i['codigo'] for i in u['4.3']) if isinstance(u.get('4.3'), list) else '',
'physicalCharacteristics': u.get('4.4'), 'findingAids': u.get('4.5'),
'locationOfOriginals': texto(u, '5.1'), 'locationOfCopies': texto(u, '5.2'),
'relatedUnitsOfDescription': texto(u, '5.3'), 'publicationNote': texto(u, '5.4'),
'generalNote': '\n'.join(x for x in [u.get('6.1'), texto(u, '6.2')] if x),
'subjectAccessPoints': '|'.join(ca.get('assuntos') or []),
'placeAccessPoints': '|'.join(ca.get('lugares') or []),
'nameAccessPoints': '|'.join(ca.get('nomes') or []),
'descriptionIdentifier': u['id'], 'rules': u.get('7.2') or '',
'archivistNote': u.get('7.1'),
'eventDates': p.get('forma'), 'eventTypes': 'Produção',
'eventStartDates': f"{p['inicio']}-01-01" if p.get('inicio') else '',
'eventEndDates': f"{p['fim']}-12-31" if p.get('fim') else '',
'eventActors': '|'.join(x['forma'] for x in u['2.1'] if x.get('id')),
'culture': 'pt_BR',
})
+487
View File
@@ -0,0 +1,487 @@
"""Monta a descrição multinível (níveis 0–5) a partir do catálogo, do ledger do
bucket e dos posts do blog. Escreve descricao/unidades.jsonl,
descricao/autoridades.jsonl e as tabelas de revisão.
Cada unidade é um objeto com `id` (= código de referência), `pai`, `nivel` e os
elementos da NOBRADE pelo número: "1.1", "1.2", … "8.1".
"""
from __future__ import annotations
import ast
import json
import re
import sqlite3
from collections import Counter, defaultdict
from datetime import date, datetime
import polars as pl
from . import campos, datas, series
from .autoridades import Autoridades
from .config import (ACESSO, BUCKET, CATALOGO, COLECAO, COLECAO_TITULO, ENTIDADE_NOME, HANDLE_URL,
INSTITUICOES, LEDGER, ORIGEM_NOME, ORIGEM_SITE, POSTS, REGRAS, RESPONSAVEL, REVISAO,
SAIDA, TEXTOS, codigo)
NIVEIS = {0: 'acervo da entidade custodiadora', 1: 'coleção', 2: 'seção', 3: 'série',
4: 'dossiê', 5: 'item documental'}
MESES_ABNT = ['jan.', 'fev.', 'mar.', 'abr.', 'maio', 'jun.', 'jul.', 'ago.', 'set.', 'out.', 'nov.', 'dez.']
HOJE = date.today().isoformat()
# ── leitura das fontes ──────────────────────────────────────────────────────
def _valores(item: dict) -> dict[str, list[str]]:
vs = defaultdict(list)
for row in item.get('full_table') or []:
v = (row.get('value') or '').strip()
if v and v not in vs[row['field']]:
vs[row['field']].append(v)
return vs
def _ledger() -> dict[str, list[dict]]:
arquivos = defaultdict(list)
if not LEDGER.exists():
return arquivos
con = sqlite3.connect(LEDGER)
for h, nome, b, sha, quando, tipo in con.execute(
'select handle, nome, bytes, sha256, quando, tipo from enviados order by handle, tipo, nome'):
arquivos[h].append({'nome': nome, 'bytes': b, 'sha256': sha, 'quando': quando, 'tipo': tipo})
return arquivos
def _abnt(post: dict) -> str:
autor = (post.get('autor') or '').strip()
partes = autor.split()
autor_abnt = f'{partes[-1].upper()}, {" ".join(partes[:-1])}' if len(partes) > 1 else autor.upper()
d = datetime.fromisoformat(post['data_iso'][:10])
acesso = (post.get('fetched_at') or HOJE)[:10]
a = datetime.fromisoformat(acesso)
return (f"{autor_abnt}. {post['titulo']}. {ORIGEM_NOME}, Rio de Janeiro, "
f"{d.day} {MESES_ABNT[d.month - 1]} {d.year}. Disponível em: {post['url']}. "
f"Acesso em: {a.day} {MESES_ABNT[a.month - 1]} {a.year}.")
def _posts() -> tuple[dict[str, list[dict]], list[dict]]:
por_handle, todos = defaultdict(list), []
if not POSTS.exists():
return por_handle, todos
for linha in POSTS.open(encoding='utf-8'):
p = json.loads(linha)
if p.get('erro') or not p.get('titulo'):
continue
hs = p.get('handles_referenciados') or []
if isinstance(hs, str):
hs = ast.literal_eval(hs)
cats = p.get('categorias') or []
if isinstance(cats, str):
cats = ast.literal_eval(cats)
ref = {'titulo': p['titulo'], 'url': p['url'], 'autor': p.get('autor'), 'data': p['data_iso'][:10],
'categorias': cats, 'abnt': _abnt(p)}
todos.append(ref)
for h in hs:
por_handle[h].append(ref)
return por_handle, todos
def _textos(caminho) -> dict[str, str]:
"""Um .md com seções "## 2.3 História arquivística" → {'2.3': texto}."""
if not caminho.exists():
return {}
out, atual, buf = {}, None, []
for linha in caminho.read_text(encoding='utf-8').splitlines():
if m := re.match(r'^##\s+(\d\.\d)\b', linha):
if atual:
out[atual] = '\n'.join(buf).strip()
atual, buf = m[1], []
elif atual:
buf.append(linha)
if atual:
out[atual] = '\n'.join(buf).strip()
return {k: v for k, v in out.items() if v}
def _mb(b: int) -> str:
return f'{b / 1e6:.1f} MB'.replace('.', ',') if b < 1e9 else f'{b / 1e9:.1f} GB'.replace('.', ',')
def _formato(nome: str) -> str:
ext = nome.rsplit('.', 1)[-1].lower() if '.' in nome else ''
return {'jpg': 'JPEG', 'jpeg': 'JPEG', 'png': 'PNG', 'tif': 'TIFF', 'tiff': 'TIFF', 'webp': 'WebP',
'pdf': 'PDF', 'gif': 'GIF'}.get(ext, ext.upper() or 'desconhecido')
def _limites(ds: list[dict]) -> dict:
ini = [d['inicio'] for d in ds if d and d.get('inicio')]
fim = [d['fim'] for d in ds if d and d.get('fim')]
if not ini and not fim:
return {'forma': '[s.d.]', 'iso': None, 'inicio': None, 'fim': None, 'qualidade': None,
'tipo': 'produção'}
a, b = min(ini or fim), max(fim or ini)
return {'forma': f'{a}-{b}' if a != b else str(a), 'iso': f'{a}/{b}' if a != b else str(a),
'inicio': a, 'fim': b, 'qualidade': 'datas-limite', 'tipo': 'produção'}
def _dimensao(especies: Counter, n_itens: int, bytes_: int) -> dict:
partes = [f'{n} {e}' for e, n in especies.most_common()]
return {'por_especie': dict(especies), 'arquivos_digitais': n_itens, 'bytes': bytes_,
'texto': f"iconográfico: {', '.join(partes)}; eletrônico: {n_itens} arquivos digitais ({_mb(bytes_)})"}
# ── montagem ────────────────────────────────────────────────────────────────
def monta():
SAIDA.mkdir(exist_ok=True)
REVISAO.mkdir(parents=True, exist_ok=True)
ledger = _ledger()
posts_de, posts = _posts()
itens = []
for linha in CATALOGO.open(encoding='utf-8'):
if linha.strip():
it = json.loads(linha)
it['_v'] = _valores(it)
itens.append(it)
# séries (nível 3)
fontes = [(it['handle'], it['community'], (it['_v']['dc.source'] or [None])[0]) for it in itens]
serie_de, series_ = series.monta(fontes)
# autoridades
aut = Autoridades()
for it in itens:
for f in ('dc.contributor', 'dc.contributor.author', 'dc.contributor.other'):
for v in it['_v'][f]:
aut.registra(v)
aut.resolve()
for reg in aut.registros.values(): # biografias no blog (3.4) → fontes da autoridade
if reg['tipo'] == 'pessoa' and ',' in reg['nome']:
sob, nome = [x.strip() for x in reg['nome'].split(',', 1)]
primeiro = nome.split()[0] if nome else ''
for p in posts:
if 'Biografia' in p['categorias'] and sob in p['titulo'] and primeiro in p['titulo']:
reg['fontes'].append(p['abnt'])
unidades: dict[str, dict] = {}
filhos = defaultdict(list)
rev_datas, rev_tipos, rev_direitos, rev_lugares = [], [], [], []
def add(u: dict):
unidades[u['id']] = u
if u['pai']:
filhos[u['pai']].append(u['id'])
# níveis 4 e 5
for it in itens:
v, h = it['_v'], it['handle']
inst = it['community']
sigla_i, nome_i, cidade_i = INSTITUICOES[inst]
sg, notacao = serie_de[h]
num = h.rsplit('/', 1)[-1]
cod = codigo(COLECAO, sigla_i, sg, num)
pasta = h.replace('/', '_')
titulo = (v['dc.title'] or [it.get('title') or ''])[0].strip()
titulo_atribuido = False
if not titulo: # proc. 1.2: título atribuído a partir da própria unidade, entre colchetes
base = next((x for x in v['dc.description'] + v['dc.subject'] + v['dc.coverage']
if not campos.corrompido(x)), 'Sem título')
titulo, titulo_atribuido = f"[{base.split('. ')[0][:90]}]", True
d = datas.interpreta((v['dc.date'] or [''])[0])
data = d.registro()
if len(v['dc.date']) > 1:
data['notas'] = (data['notas'] or []) + [f'outra data na origem: {x}' for x in v['dc.date'][1:]]
produtores = []
for f in ('dc.contributor', 'dc.contributor.author', 'dc.contributor.other'):
for nome in v[f]:
aid = aut.id(nome)
if aid and aid not in [p['id'] for p in produtores]:
produtores.append({'id': aid, 'forma': aut[aid]['forma_autorizada'],
'funcao': 'autor' if f != 'dc.contributor.other' else 'outro'})
if not produtores:
produtores = [{'id': None, 'forma': 'Autoria não identificada', 'funcao': 'autor'}]
descricoes = [x for x in v['dc.description'] if not campos.corrompido(x)]
fisico = [x for x in descricoes if campos.e_fisico(x)]
conteudo = [x for x in descricoes if x not in fisico]
esp = campos.especie((v['dc.type'] or [None])[0])
cor = campos.cor(fisico)
arquivos = ledger.get(h, [])
preserv = sorted((a for a in arquivos if a['tipo'] == 'preservacao'),
key=lambda a: (a['nome'] != 'imagem.jpg', a['nome']))
imagens = preserv or [a for a in arquivos if a['tipo'] == 'thumbnail']
total = sum(a['bytes'] or 0 for a in imagens)
direitos = campos.direitos(v['dc.rights'] + [str(it.get('rights') or '')], nome_i)
lugar = campos.lugar(v['dc.coverage'])
assuntos = [s for s in v['dc.subject'] if not campos.corrompido(s)]
codigo_origem = next((re.sub(r'\.\w{3,4}$', '', x) for x in v['dc.identifier'] + v['dc.description']
if re.match(r'BR ?[A-Z]{2}[A-Z]{2,}\s', x)), None)
sophia = next((x for x in v['dc.relation'] if 'sophia' in x), None)
objdigital = [x for x in v['dc.identifier'] if 'objdigital' in x]
notas = ['Título atribuído pelo arquivista: a origem não informa título.'] if titulo_atribuido else []
if d.original and data['forma'] != d.original:
notas.append(f'Data como consta na origem: {d.original}')
notas += data['notas'] or []
if esp['presumida']:
notas.append('Espécie documental não informada na origem; presumida fotografia'
+ (f" (valor na origem: {esp['original']})" if esp.get('original') else '') + '.')
if direitos['originais']:
notas.append('Direitos como constam na origem: ' + ' | '.join(direitos['originais']))
lixo = [f"{f}: {x[:60]}" for f, xs in v.items() for x in xs if campos.corrompido(x)
and f in ('dc.type', 'dc.rights', 'dc.source', 'dc.subject', 'dc.date', 'dc.coverage')]
if lixo:
notas.append('Valores corrompidos na origem, desconsiderados: ' + '; '.join(lixo))
conservacao = None
if not preserv:
conservacao = ('Arquivo de preservação indisponível na origem (o repositório responde HTTP 500 '
'ao bitstream; ver errors.md). A cópia guarda apenas a miniatura gerada pelo DSpace.')
dossie = {
'id': cod, 'pai': codigo(COLECAO, sigla_i, sg), 'nivel': 4, 'handle': h,
'1.1': cod,
'1.2': {'titulo': titulo, 'atribuido': titulo.startswith('[')},
'1.3': {'producao': data, 'topica': lugar},
'1.4': {'nivel': 4, 'nome': NIVEIS[4]},
'1.5': {'genero': esp['genero'], 'especie': esp['especie'], 'suporte': esp['suporte'], 'cor': cor,
'fisico': fisico or None, 'arquivos_digitais': len(imagens), 'bytes': total,
'texto': (f"1 {esp['especie']}" + (f' {cor}' if cor else '')
+ (f", {esp['suporte']}" if esp['suporte'] else '')
+ (f" ({'; '.join(fisico)})" if fisico else '')
+ f"; {len(imagens)} arquivo{'s' if len(imagens) != 1 else ''} digita"
+ f"{'is' if len(imagens) != 1 else 'l'} ({_mb(total)})")},
'2.1': produtores,
'2.3': (f"Registrado no repositório DSpace da {ORIGEM_NOME}"
+ (f" em {v['dc.date.accessioned'][0][:10]}" if v['dc.date.accessioned'] else '')
+ f". Cópia digital capturada em {it['fetched_at'][:10]} e armazenada em "
f"{BUCKET}/itens/{pasta}/ com SHA-256 de cada arquivo."),
'2.4': (f"{ORIGEM_NOME} ({ORIGEM_SITE}), repositório mantido pela Biblioteca Nacional; "
f"coleta combinada com a Biblioteca Nacional, em {it['fetched_at'][:10]}. Handle {h}."),
'3.1': ' '.join(conteudo) or None,
'4.2': direitos,
'4.3': campos.idiomas(v['dc.language']) or None,
'4.4': (f"Arquivo{'s' if len(imagens) > 1 else ''} digita{'is' if len(imagens) > 1 else 'l'} "
f"{', '.join(sorted({_formato(a['nome']) for a in imagens})) or '—'}; "
'abre em qualquer visualizador de imagem.'
+ (f" Original: {'; '.join(fisico)}." if fisico else '')),
'5.1': {'instituicao': nome_i, 'local': cidade_i, 'url': HANDLE_URL.format(h),
'codigo_na_origem': codigo_origem, 'notacao_na_origem': notacao, 'sophia': sophia,
'texto': f"Original sob a guarda de {nome_i}, {cidade_i}"
+ (f", código {codigo_origem}" if codigo_origem else '')
+ (f", notação {notacao}" if notacao else '') + f". {HANDLE_URL.format(h)}"},
'5.2': {'nesta_entidade': [{'tipo': a['tipo'], 'chave': (f"{BUCKET}/derivados/thumb256/{a['nome']}"
if a['tipo'] == 'derivado-thumb256'
else f"{BUCKET}/itens/{pasta}/{a['tipo']}/{a['nome']}"),
'bytes': a['bytes'], 'sha256': a['sha256']} for a in arquivos],
'em_outras_entidades': [{'entidade': 'Biblioteca Nacional (Brasil) — BNDigital', 'url': u}
for u in objdigital] or None},
'5.3': (v['dc.relation.ispartof'] + v['dcterms.relation']) or None,
'5.4': [p['abnt'] for p in posts_de.get(h, [])] or None,
'6.1': conservacao,
'6.2': notas or None,
'7.1': (f'Descrição gerada pelo pipeline/nobrade a partir dos metadados Dublin Core colhidos '
f'da {ORIGEM_NOME} ({it["source_url"]}); responsável: {RESPONSAVEL}.'),
'7.3': {'coleta': it['fetched_at'][:10], 'descricao': HOJE},
'8.1': {'assuntos': [s for s in assuntos if campos.idioma_termo(s) == 'por'] or None,
'assuntos_eng': [s for s in assuntos if campos.idioma_termo(s) == 'eng'] or None,
'lugares': [c for c in v['dc.coverage'] if not campos.corrompido(c)] or None,
'nomes': [p['forma'] for p in produtores if p['id']] or None,
'periodo': data['iso']},
'_sd': not d.ok, '_especie': esp['especie'], '_serie': (inst, sg),
}
add(dossie)
rev_datas.append({'handle': h, 'original': d.original, 'forma': data['forma'], 'iso': data['iso'],
'inicio': data['inicio'], 'fim': data['fim'], 'qualidade': data['qualidade'],
'motivo': data['motivo']})
rev_tipos.append({'instituicao': inst, 'dc_type': (v['dc.type'] or [''])[0], 'genero': esp['genero'],
'especie': esp['especie'], 'suporte': esp['suporte'] or '', 'presumida': esp['presumida']})
rev_direitos.append({'instituicao': inst, 'categoria': direitos['categoria'], 'detentor': direitos['detentor'],
'originais': ' | '.join(direitos['originais'] or [])})
rev_lugares.append({'coverage': ' | '.join(v['dc.coverage']), 'data_topica': lugar or ''})
for i, a in enumerate(imagens, 1):
ci = f'{cod}.{i:02d}'
add({
'id': ci, 'pai': cod, 'nivel': 5, 'handle': h,
'1.1': ci,
'1.2': {'titulo': f"{titulo} [imagem {i} de {len(imagens)}]", 'atribuido': True},
'1.3': {'producao': data},
'1.4': {'nivel': 5, 'nome': NIVEIS[5]},
'1.5': {'genero': 'eletrônico', 'especie': 'arquivo de imagem', 'bytes': a['bytes'],
'texto': f"1 arquivo digital {_formato(a['nome'])} ({_mb(a['bytes'] or 0)})"},
'2.1': produtores,
'4.4': f"{_formato(a['nome'])}; SHA-256 {a['sha256']}"
+ ('; miniatura — preservação indisponível na origem' if a['tipo'] == 'thumbnail' else ''),
'5.2': {'nesta_entidade': [{'tipo': a['tipo'], 'chave': f"{BUCKET}/itens/{pasta}/{a['tipo']}/{a['nome']}",
'bytes': a['bytes'], 'sha256': a['sha256']}]},
'7.3': {'descricao': HOJE},
})
# níveis 3, 2, 1, 0 — de baixo para cima, agregando os filhos
textos1 = _textos(TEXTOS / 'nivel1.md')
textos0 = _textos(TEXTOS / 'nivel0.md')
por_serie = defaultdict(list)
for u in unidades.values():
if u['nivel'] == 4:
por_serie[u['_serie']].append(u)
# datas atribuídas aos s.d. (proc. 1.3.3.2): período do fotógrafo, senão datas-limite da série
rev_por_handle = {r['handle']: r for r in rev_datas}
lim_secao = {inst: _limites([u['1.3']['producao'] for (i, _), us in por_serie.items() if i == inst
for u in us if not u['_sd']]) for inst, _ in por_serie}
lim_serie = {k: _limites([u['1.3']['producao'] for u in us if not u['_sd']]) for k, us in por_serie.items()}
for k, us in por_serie.items():
for u in us:
if not u['_sd']:
continue
per = next((aut[p['id']]['periodo_atividade'] for p in u['2.1']
if p['id'] and aut[p['id']]['periodo_atividade']), None)
if per:
nova = datas.atribuida(*per, 'período de atividade do autor')
elif lim_serie[k]['inicio']:
nova = datas.atribuida(lim_serie[k]['inicio'], lim_serie[k]['fim'], 'datas-limite da série')
elif lim_secao[k[0]]['inicio']:
nova = datas.atribuida(lim_secao[k[0]]['inicio'], lim_secao[k[0]]['fim'],
'datas-limite da instituição de origem')
else:
continue
nova['original'] = u['1.3']['producao']['original']
nova['notas'] = nova['notas'] + (u['1.3']['producao']['notas'] or [])
u['1.3']['producao'] = nova
u['8.1']['periodo'] = nova['iso']
for fid in filhos[u['id']]:
unidades[fid]['1.3']['producao'] = nova
r = rev_por_handle[u['handle']]
r.update(forma=nova['forma'], iso=nova['iso'], inicio=nova['inicio'], fim=nova['fim'],
qualidade='atribuída pelo arquivista')
def agrega(us: list[dict]) -> dict:
esp = Counter(u['_especie'] for u in us)
n = sum(u['1.5']['arquivos_digitais'] for u in us)
b = sum(u['1.5']['bytes'] for u in us)
autores = Counter(p['forma'] for u in us for p in u['2.1'] if p['id'])
lugares = Counter(u['1.3']['topica'] for u in us if u['1.3'].get('topica'))
return {'data': _limites([u['1.3']['producao'] for u in us]), 'dim': _dimensao(esp, n, b),
'autores': autores, 'lugares': lugares, 'dossies': len(us)}
def resumo(a: dict) -> str:
s = f"{a['dossies']} dossiês, {a['data']['forma']}."
if a['autores']:
s += ' Principais autores: ' + '; '.join(f'{k} ({n})' for k, n in a['autores'].most_common(5)) + '.'
if a['lugares']:
s += ' Principais lugares: ' + '; '.join(f'{k} ({n})' for k, n in a['lugares'].most_common(5)) + '.'
return s
rev_series = []
por_secao = defaultdict(list)
for (inst, sg), us in sorted(por_serie.items()):
sigla_i, nome_i, cidade_i = INSTITUICOES[inst]
info = series_[(inst, sg)]
cod = codigo(COLECAO, sigla_i, sg)
a = agrega(us)
t = _textos(TEXTOS / 'series' / f'{sigla_i}.{sg}.md')
titulo = info['titulo'] if sg != 'AV' else f'Avulsos — {nome_i}'
produtor = re.sub(r'(?i)^(cole[cç][aã]o( particular)?|fundo|arquivo|s[ée]rie|conv[eê]nio)\s+(d[aeo]s?\s+)?', '', titulo)
add({
'id': cod, 'pai': codigo(COLECAO, sigla_i), 'nivel': 3,
'1.1': cod, '1.2': {'titulo': titulo, 'atribuido': sg == 'AV'},
'1.3': {'producao': a['data']}, '1.4': {'nivel': 3, 'nome': NIVEIS[3]},
'1.5': a['dim'],
'2.1': [{'id': None, 'forma': nome_i if sg == 'AV' else produtor, 'funcao': 'colecionador'}],
'2.2': t.get('2.2'),
'3.1': t.get('3.1') or resumo(a),
'3.4': t.get('3.4') or ('Dossiês ordenados pelo número do handle na origem.' if sg != 'AV' else
'Reúne os dossiês sem coleção/fundo de origem identificável em dc.source; '
'a notação da origem, quando há, fica em 5.1 de cada dossiê.'),
'5.1': {'instituicao': nome_i, 'local': cidade_i,
'variantes_na_origem': dict(info['variantes'].most_common()) or None},
'7.3': {'descricao': HOJE},
})
por_secao[inst].extend(us)
for var, n in (info['variantes'].most_common() or [('', info['n'])]):
rev_series.append({'instituicao': inst, 'codigo': cod, 'titulo': titulo, 'dc_source': var, 'n': n})
todos = []
for inst, us in sorted(por_secao.items(), key=lambda kv: -len(kv[1])):
sigla_i, nome_i, cidade_i = INSTITUICOES[inst]
cod = codigo(COLECAO, sigla_i)
a = agrega(us)
t = _textos(TEXTOS / 'secoes' / f'{sigla_i}.md')
add({
'id': cod, 'pai': codigo(COLECAO), 'nivel': 2,
'1.1': cod, '1.2': {'titulo': f'Seção {nome_i}', 'atribuido': True},
'1.3': {'producao': a['data']}, '1.4': {'nivel': 2, 'nome': NIVEIS[2]},
'1.5': a['dim'],
'2.1': [{'id': None, 'forma': nome_i, 'funcao': 'instituição custodiadora dos originais'}],
'2.2': t.get('2.2'),
'3.1': t.get('3.1') or resumo(a),
'3.4': f"{len(filhos[cod])} séries, por coleção ou fundo de origem.",
'5.1': {'instituicao': nome_i, 'local': cidade_i},
'7.3': {'descricao': HOJE},
})
todos.extend(us)
a = agrega(todos)
c1 = codigo(COLECAO)
add({
'id': c1, 'pai': codigo(), 'nivel': 1,
'1.1': c1, '1.2': {'titulo': COLECAO_TITULO, 'atribuido': False},
'1.3': {'producao': a['data'], 'acumulacao': {'forma': '2026', 'iso': '2026'}},
'1.4': {'nivel': 1, 'nome': NIVEIS[1]}, '1.5': a['dim'],
'2.1': [{'id': None, 'forma': ENTIDADE_NOME, 'funcao': 'colecionador'}],
'2.2': textos1.get('2.2'), '2.3': textos1.get('2.3'), '2.4': textos1.get('2.4'),
'3.1': textos1.get('3.1') or resumo(a), '3.2': textos1.get('3.2'), '3.3': textos1.get('3.3'),
'3.4': textos1.get('3.4'),
'4.1': textos1.get('4.1') or ACESSO, '4.2': textos1.get('4.2'),
'4.3': textos1.get('4.3'), '4.4': textos1.get('4.4'), '4.5': textos1.get('4.5'),
'5.1': textos1.get('5.1'), '5.4': textos1.get('5.4'),
'6.2': textos1.get('6.2'),
'7.1': textos1.get('7.1'), '7.2': REGRAS, '7.3': {'descricao': HOJE},
'8.1': textos1.get('8.1'),
})
c0 = codigo()
add({
'id': c0, 'pai': None, 'nivel': 0,
'1.1': c0, '1.2': {'titulo': f'Acervo {ENTIDADE_NOME}', 'atribuido': False},
'1.3': {'producao': a['data']}, '1.4': {'nivel': 0, 'nome': NIVEIS[0]}, '1.5': a['dim'],
'2.1': [{'id': None, 'forma': ENTIDADE_NOME, 'funcao': 'entidade custodiadora'}],
'2.2': textos0.get('2.2'), '3.1': textos0.get('3.1'),
'4.1': textos0.get('4.1') or ACESSO, '7.2': REGRAS, '7.3': {'descricao': HOJE},
})
# 1.4: títulos dos níveis superiores (proc. 1.1.4)
for u in unidades.values():
cad, p = [], u['pai']
while p:
cad.append(unidades[p]['1.2']['titulo'])
p = unidades[p]['pai']
u['1.4']['hierarquia'] = list(reversed(cad)) or None
ordem = sorted(unidades.values(), key=lambda u: (u['nivel'], u['id']))
with (SAIDA / 'unidades.jsonl').open('w', encoding='utf-8') as f:
for u in ordem:
f.write(json.dumps({k: x for k, x in u.items() if not k.startswith('_') and x is not None},
ensure_ascii=False) + '\n')
with (SAIDA / 'autoridades.jsonl').open('w', encoding='utf-8') as f:
for r in aut.registros.values():
f.write(json.dumps(r, ensure_ascii=False) + '\n')
# tabelas de revisão
pl.DataFrame(rev_datas, infer_schema_length=None).filter(pl.col('qualidade').is_null() | (pl.col('qualidade') != 'exata')) \
.sort('motivo', 'original', nulls_last=True).write_csv(REVISAO / 'datas.tsv', separator='\t')
pl.DataFrame(rev_series, infer_schema_length=None).sort('codigo', 'n', descending=[False, True]) \
.write_csv(REVISAO / 'series.tsv', separator='\t')
pl.DataFrame(rev_tipos, infer_schema_length=None).group_by(pl.all()).len('n').sort('n', descending=True) \
.write_csv(REVISAO / 'tipos.tsv', separator='\t')
pl.DataFrame(rev_direitos, infer_schema_length=None).group_by(pl.all()).len('n').sort('n', descending=True) \
.write_csv(REVISAO / 'direitos.tsv', separator='\t')
pl.DataFrame(rev_lugares, infer_schema_length=None).group_by(pl.all()).len('n').sort('n', descending=True) \
.write_csv(REVISAO / 'lugares.tsv', separator='\t')
pl.DataFrame([{'id': r['id'], 'forma_autorizada': r['forma_autorizada'], 'tipo': r['tipo'],
'ocorrencias': r['ocorrencias'], 'variantes': ' | '.join(r['variantes'])}
for r in aut.registros.values()], infer_schema_length=None).write_csv(REVISAO / 'autoridades.tsv', separator='\t')
return unidades, aut
+51
View File
@@ -0,0 +1,51 @@
"""Leva a descrição NOBRADE para o mural: grava no `meta` de cada peça do
web/atlas/atlas-map.json o código de referência, a data normalizada, a série
e o suporte, sem re-renderizar os atlas .webp.
python -m nobrade.mural (de dentro de pipeline/, depois de python -m nobrade)
Campos novos em meta (curtos: o mapa inteiro desce para o navegador):
ref código de referência (1.1) dt data na forma da NOBRADE (1.3)
ano ano inicial, para o histograma si índice em `series` do mapa (nível 3)
sup espécie e suporte (1.5) rep categoria de reprodução (4.2)
"""
import json
from .config import RAIZ, SAIDA
MAPA = RAIZ / 'web' / 'atlas' / 'atlas-map.json'
def main():
series, dossies = {}, {}
for linha in (SAIDA / 'unidades.jsonl').open(encoding='utf-8'):
u = json.loads(linha)
if u['nivel'] == 3:
series[u['id']] = u['1.2']['titulo']
elif u['nivel'] == 4:
dossies[u['handle']] = u
d = json.loads(MAPA.read_text(encoding='utf-8'))
titulos = sorted(set(series.values()), key=str.casefold)
idx = {t: i for i, t in enumerate(titulos)}
d['series'] = titulos
feitos = 0
for h, e in d['map'].items():
u = dossies.get(h)
if not u:
continue
p = u['1.3']['producao']
dim = u['1.5']
sup = dim['especie'] + (f" {dim['cor']}" if dim.get('cor') else '') + (f", {dim['suporte']}" if dim.get('suporte') else '')
e['meta'].update({
'ref': u['1.1'], 'dt': p.get('forma'), 'ano': p.get('inicio') or p.get('fim'),
'si': idx[series[u['pai']]], 'sup': sup, 'rep': u['4.2']['categoria'],
})
feitos += 1
MAPA.write_text(json.dumps(d, ensure_ascii=False, separators=(',', ':')), encoding='utf-8')
print(f'{feitos} de {len(d["map"])} peças com descrição NOBRADE; {len(titulos)} séries')
if __name__ == '__main__':
main()
+165
View File
@@ -0,0 +1,165 @@
"""Nível 3 — séries a partir de `dc.source`.
O campo traz, misturados, o nome da coleção/fundo de origem ("Coleção Gilberto
Ferrez" e "Gilberto Ferrez"), sufixos da instituição ("… / Museu da
República"), notações de caixa ("CX 14") e lixo de extração. A regra:
1. limpa o valor até uma chave (sem prefixo Coleção/Fundo/Arquivo, sem sufixo
institucional, sem notação no fim, sem acento, sem pontuação);
2. chaves com pelo menos MINIMO itens viram série;
3. valor raro que contém a chave de uma série vai para ela (os "Negativo de
vidro MPEG639, Coleção Fotográfica do Museu Paraense…");
4. o resto vai para a série AV (Avulsos) da instituição, e o valor original
fica como notação na origem (5.1).
Correções manuais em `ajustes/series.tsv` (instituicao, dc.source, titulo)
prevalecem sobre a regra.
"""
from __future__ import annotations
import csv
import re
import unicodedata
from collections import Counter, defaultdict
from .config import AJUSTES
MINIMO = 3
# variantes que a limpeza não junta sozinha: chave → chave canônica
ALIAS = {
'd teresa cristina maria': 'thereza christina maria',
'teresa cristina maria': 'thereza christina maria',
'federacao brasileira para o progresso feminino fbpf': 'federacao brasileira pelo progresso feminino',
'federacao brasileira para o progresso feminino': 'federacao brasileira pelo progresso feminino',
'fotografica mpeg': 'fotografica do museu paraense emilio goeldi',
'brascan cem anos no brasil': 'brascan cem anos no brasil',
'escola de ciencias sociais fgv cpdoc': 'escola de ciencias sociais fgv cpdoc',
'escola de ciencias sociais': 'escola de ciencias sociais fgv cpdoc',
'dos eventos institucionais': 'eventos institucionais',
'mestres do sec xix': 'mestres do seculo xix',
'cristovao barcellos': 'cristovao barcelos',
}
# notação de caixa/negativo/foto: é localização na origem (5.1), não série
NOTACAO = re.compile(r'(?i)^\s*(cx|caixas?|nv|foto|negativo|estampa)\b')
PREFIXO = re.compile(r'^(convenio|colecao particular|colecao|fundo|arquivo|acervo|serie)\s+(d[aeo]s?\s+)?')
LIXO = re.compile(r'[<>{}]|ns:|^[0-9a-f]{12,}')
def sem_acento(s: str) -> str:
return ''.join(c for c in unicodedata.normalize('NFD', s) if unicodedata.category(c) != 'Mn')
def limpa(v: str) -> str:
s = v.strip()
s = re.sub(r'\s*/\s*(acervo|museu|ibge|instituto moreira).*$', '', s, flags=re.I)
s = re.sub(r'\s+-\s+(museu|funda|fgv|ibge).*$', '', s, flags=re.I)
s = re.sub(r'\s*\((museu|ibram)[^)]*\)', '', s, flags=re.I)
s = re.sub(r'\s*/\s*ibge$', '', s, flags=re.I)
s = re.sub(r'\s*(?:-\s*|\()\s*\w*\d\w*\)?\s*$', '', s) # "- 1123K", "(148T)", "- EFi9"
s = sem_acento(s.lower())
s = re.sub(r'\bsec\.?\s', 'sec ', s)
s = re.sub(r'[^\w\s]', ' ', s)
s = re.sub(r'\s+', ' ', s).strip()
s = PREFIXO.sub('', s)
return ALIAS.get(s, s)
def sigla(titulo: str, usadas: set[str]) -> str:
if m := re.match(r'(?i)[áa]lbum\s+(\d+)', titulo):
base = f'A{m[1]}'
usadas.add(base)
return base
miolo = PREFIXO.sub('', sem_acento(titulo.lower()))
palavras = [p for p in re.findall(r'[a-z0-9]+', miolo) if p not in {'de', 'da', 'do', 'das', 'dos', 'e', 'a', 'o'}]
base = ''.join(p[0] for p in palavras).upper()[:6] or 'S'
if len(base) < 2 and palavras:
base = palavras[0][:4].upper()
s, n = base, 2
while s in usadas or s == 'AV':
s, n = f'{base}{n}', n + 1
usadas.add(s)
return s
def _titulo(variantes: Counter) -> str:
"""A variante mais frequente; se ela não diz o que é, herda o tipo
(Coleção/Fundo/Série) de outra variante — "Thereza Christina Maria" +
"Coleção D. Teresa…" → "Coleção Thereza Christina Maria"."""
tipo_re = r'(?i)^(cole[cç][aã]o( particular)?|fundo|arquivo|s[ée]rie|conv[eê]nio|[áa]lbum)\b'
_, v = max((n, v) for v, n in variantes.items())
v = re.sub(r'\s+', ' ', v).strip()
v = re.sub(r'\s*[-/]\s*(Acervo|Museu|Fundação|Instituto Moreira|IBGE).*$', '', v)
v = re.sub(r'\s*\((Museu|IBRAM)[^)]*\)', '', v)
if not re.match(tipo_re, v):
tipos = Counter(m[1].capitalize() for x in variantes if (m := re.match(tipo_re, x.strip())))
v = f"{tipos.most_common(1)[0][0] if tipos else 'Coleção'} {v}"
return v
def _ajustes() -> dict[tuple[str, str], str]:
p = AJUSTES / 'series.tsv'
if not p.exists():
return {}
with p.open(encoding='utf-8') as f:
return {(r['instituicao'], r['dc_source']): r['titulo'] for r in csv.DictReader(f, delimiter='\t')}
def monta(fontes: list[tuple[str, str, str | None]]):
"""fontes: (handle, instituição, dc.source | None).
Devolve (por_handle, series): por_handle[handle] = (sigla, notação na origem
ou None); series[(instituição, sigla)] = {'titulo', 'variantes', 'n'}.
"""
ajuste = _ajustes()
chaves = defaultdict(Counter) # (inst, chave) → Counter(valor original)
for _, inst, v in fontes:
if v and not LIXO.search(v) and not NOTACAO.match(v) and (inst, v) not in ajuste:
chaves[(inst, limpa(v))][v] += 1
series: dict[tuple[str, str], dict] = {}
sigla_de: dict[tuple[str, str], str] = {}
usadas: dict[str, set[str]] = defaultdict(set)
fortes = defaultdict(list) # inst → [chave]
for (inst, chave), variantes in sorted(chaves.items(), key=lambda kv: -sum(kv[1].values())):
if not chave or sum(variantes.values()) < MINIMO:
continue
titulo = _titulo(variantes)
sg = sigla(titulo, usadas[inst])
sigla_de[(inst, chave)] = sg
series[(inst, sg)] = {'titulo': titulo, 'variantes': variantes, 'n': 0}
fortes[inst].append(chave)
for (inst, v), titulo in ajuste.items():
k = (inst, 'ajuste:' + titulo)
if k not in sigla_de:
sg = sigla(titulo, usadas[inst])
sigla_de[k] = sg
series[(inst, sg)] = {'titulo': titulo, 'variantes': Counter(), 'n': 0}
por_handle = {}
for handle, inst, v in fontes:
sg = None
if v and (inst, v) in ajuste:
sg = sigla_de[(inst, 'ajuste:' + ajuste[(inst, v)])]
series[(inst, sg)]['variantes'][v] += 1
elif v and not LIXO.search(v):
chave = limpa(v)
sg = sigla_de.get((inst, chave))
if sg is None:
# o valor raro contém o nome de uma série forte da mesma instituição?
for forte in sorted(fortes[inst], key=len, reverse=True):
if len(forte) > 5 and re.search(rf'\b{re.escape(forte)}\b', chave):
sg = sigla_de[(inst, forte)]
series[(inst, sg)]['variantes'][v] += 1
break
if sg is None:
sg = 'AV'
series.setdefault((inst, 'AV'), {'titulo': 'Avulsos', 'variantes': Counter(), 'n': 0})
series[(inst, sg)]['n'] += 1
# o valor original fica como notação na origem quando não é o próprio nome da série
notacao = v if v and (sg == 'AV' or limpa(v) not in {limpa(x) for x in [series[(inst, sg)]['titulo']]}) else None
por_handle[handle] = (sg, notacao)
return por_handle, series
+85
View File
@@ -0,0 +1,85 @@
"""Validador dos elementos obrigatórios da NOBRADE, por nível.
Obrigatórios: 1.1, 1.2, 1.3 (data de produção), 1.4, 1.5, 2.1; 4.1 só nos
níveis 0 e 1. Além deles, lista avisos que não reprovam mas pedem revisão.
Escreve descricao/pendencias.md e devolve o número de pendências.
"""
from __future__ import annotations
from collections import Counter, defaultdict
from .config import SAIDA
def verifica(u: dict) -> tuple[list[str], list[str]]:
erros, avisos = [], []
n = u['nivel']
if not u.get('1.1'):
erros.append('1.1 código de referência ausente')
if not (u.get('1.2') or {}).get('titulo', '').strip():
erros.append('1.2 título ausente')
prod = (u.get('1.3') or {}).get('producao') or {}
if not prod.get('inicio') and not prod.get('fim'):
erros.append('1.3 data de produção ausente')
if not (u.get('1.4') or {}).get('nome'):
erros.append('1.4 nível ausente')
if not (u.get('1.5') or {}).get('texto'):
erros.append('1.5 dimensão e suporte ausente')
if not u.get('2.1'):
erros.append('2.1 produtor ausente')
if n <= 1 and not u.get('4.1'):
erros.append('4.1 condições de acesso ausente (obrigatório nos níveis 0 e 1)')
if n == 4:
if prod.get('qualidade') == 'atribuída pelo arquivista' or (prod.get('notas') or [''])[0].startswith('data atribuída'):
avisos.append('1.3 data atribuída pelo arquivista — conferir')
if prod.get('motivo') == 'ilegível':
avisos.append('1.3 data da origem ilegível')
if all(p.get('id') is None for p in u.get('2.1') or []):
avisos.append('2.1 autoria não identificada')
if u['id'].split('.')[-2] == 'AV':
avisos.append('nível 3 em Avulsos — série de origem não identificada')
if any('presumida' in x for x in u.get('6.2') or []):
avisos.append('1.5 espécie presumida')
if any('corrompidos' in x for x in u.get('6.2') or []):
avisos.append('valores corrompidos na origem')
if u.get('6.1'):
avisos.append('6.1 preservação indisponível na origem')
if (u.get('4.2') or {}).get('categoria') == 'consultar o detentor':
avisos.append('4.2 condição de reprodução não informada na origem')
if not (u.get('3.1') or '').strip():
avisos.append('3.1 sem âmbito e conteúdo')
return erros, avisos
def valida(unidades) -> int:
erros, avisos = defaultdict(list), defaultdict(list)
por_nivel = Counter()
for u in unidades:
por_nivel[u['nivel']] += 1
e, a = verifica(u)
for x in e:
erros[x].append(u['id'])
for x in a:
avisos[x].append(u['id'])
total = sum(len(v) for v in erros.values())
linhas = ['# Pendências da descrição NOBRADE', '',
'Gerado por `python -m nobrade`. Obrigatórios reprovam; avisos pedem revisão.', '',
'| Nível | Unidades |', '|---|--:|']
nomes = {0: 'acervo', 1: 'coleção', 2: 'seção', 3: 'série', 4: 'dossiê', 5: 'item'}
linhas += [f'| {n} {nomes[n]} | {c:,} |'.replace(',', '.') for n, c in sorted(por_nivel.items())]
linhas += ['', f'## Obrigatórios faltando: {total}', '']
if not erros:
linhas.append('Nenhum. Todas as unidades têm os elementos obrigatórios do seu nível.')
for k, ids in sorted(erros.items(), key=lambda kv: -len(kv[1])):
linhas += [f'### {k} — {len(ids)}', '', *[f'- `{i}`' for i in ids[:50]]]
if len(ids) > 50:
linhas.append(f'- … e mais {len(ids) - 50}')
linhas.append('')
linhas += ['', '## Avisos', '', '| Aviso | Dossiês |', '|---|--:|']
linhas += [f'| {k} | {len(v):,} |'.replace(',', '.') for k, v in sorted(avisos.items(), key=lambda kv: -len(kv[1]))]
linhas.append('')
(SAIDA / 'pendencias.md').write_text('\n'.join(linhas), encoding='utf-8')
return total
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+33
View File
@@ -0,0 +1,33 @@
<?xml version="1.0" encoding="UTF-8"?>
<!-- Subconjunto do xlink.xsd da LoC (http://www.loc.gov/standards/xlink/xlink.xsd),
que responde 403 a clientes fora do navegador: só o que o cpf.xsd usa. -->
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://www.w3.org/1999/xlink"
xmlns:xlink="http://www.w3.org/1999/xlink"
attributeFormDefault="qualified">
<xs:attribute name="href" type="xs:anyURI"/>
<xs:attribute name="role" type="xs:string"/>
<xs:attribute name="arcrole" type="xs:string"/>
<xs:attribute name="title" type="xs:string"/>
<xs:attribute name="show">
<xs:simpleType><xs:restriction base="xs:string">
<xs:enumeration value="new"/><xs:enumeration value="replace"/><xs:enumeration value="embed"/>
<xs:enumeration value="other"/><xs:enumeration value="none"/>
</xs:restriction></xs:simpleType>
</xs:attribute>
<xs:attribute name="actuate">
<xs:simpleType><xs:restriction base="xs:string">
<xs:enumeration value="onLoad"/><xs:enumeration value="onRequest"/>
<xs:enumeration value="other"/><xs:enumeration value="none"/>
</xs:restriction></xs:simpleType>
</xs:attribute>
<xs:attributeGroup name="simpleLink">
<xs:attribute name="type" type="xs:string" fixed="simple" form="qualified"/>
<xs:attribute ref="xlink:href" use="optional"/>
<xs:attribute ref="xlink:role" use="optional"/>
<xs:attribute ref="xlink:arcrole" use="optional"/>
<xs:attribute ref="xlink:title" use="optional"/>
<xs:attribute ref="xlink:show" use="optional"/>
<xs:attribute ref="xlink:actuate" use="optional"/>
</xs:attributeGroup>
</xs:schema>
+287
View File
@@ -0,0 +1,287 @@
<?xml version='1.0'?>
<?xml-stylesheet href="../2008/09/xsd.xsl" type="text/xsl"?>
<xs:schema targetNamespace="http://www.w3.org/XML/1998/namespace"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns ="http://www.w3.org/1999/xhtml"
xml:lang="en">
<xs:annotation>
<xs:documentation>
<div>
<h1>About the XML namespace</h1>
<div class="bodytext">
<p>
This schema document describes the XML namespace, in a form
suitable for import by other schema documents.
</p>
<p>
See <a href="http://www.w3.org/XML/1998/namespace.html">
http://www.w3.org/XML/1998/namespace.html</a> and
<a href="http://www.w3.org/TR/REC-xml">
http://www.w3.org/TR/REC-xml</a> for information
about this namespace.
</p>
<p>
Note that local names in this namespace are intended to be
defined only by the World Wide Web Consortium or its subgroups.
The names currently defined in this namespace are listed below.
They should not be used with conflicting semantics by any Working
Group, specification, or document instance.
</p>
<p>
See further below in this document for more information about <a
href="#usage">how to refer to this schema document from your own
XSD schema documents</a> and about <a href="#nsversioning">the
namespace-versioning policy governing this schema document</a>.
</p>
</div>
</div>
</xs:documentation>
</xs:annotation>
<xs:attribute name="lang">
<xs:annotation>
<xs:documentation>
<div>
<h3>lang (as an attribute name)</h3>
<p>
denotes an attribute whose value
is a language code for the natural language of the content of
any element; its value is inherited. This name is reserved
by virtue of its definition in the XML specification.</p>
</div>
<div>
<h4>Notes</h4>
<p>
Attempting to install the relevant ISO 2- and 3-letter
codes as the enumerated possible values is probably never
going to be a realistic possibility.
</p>
<p>
See BCP 47 at <a href="http://www.rfc-editor.org/rfc/bcp/bcp47.txt">
http://www.rfc-editor.org/rfc/bcp/bcp47.txt</a>
and the IANA language subtag registry at
<a href="http://www.iana.org/assignments/language-subtag-registry">
http://www.iana.org/assignments/language-subtag-registry</a>
for further information.
</p>
<p>
The union allows for the 'un-declaration' of xml:lang with
the empty string.
</p>
</div>
</xs:documentation>
</xs:annotation>
<xs:simpleType>
<xs:union memberTypes="xs:language">
<xs:simpleType>
<xs:restriction base="xs:string">
<xs:enumeration value=""/>
</xs:restriction>
</xs:simpleType>
</xs:union>
</xs:simpleType>
</xs:attribute>
<xs:attribute name="space">
<xs:annotation>
<xs:documentation>
<div>
<h3>space (as an attribute name)</h3>
<p>
denotes an attribute whose
value is a keyword indicating what whitespace processing
discipline is intended for the content of the element; its
value is inherited. This name is reserved by virtue of its
definition in the XML specification.</p>
</div>
</xs:documentation>
</xs:annotation>
<xs:simpleType>
<xs:restriction base="xs:NCName">
<xs:enumeration value="default"/>
<xs:enumeration value="preserve"/>
</xs:restriction>
</xs:simpleType>
</xs:attribute>
<xs:attribute name="base" type="xs:anyURI"> <xs:annotation>
<xs:documentation>
<div>
<h3>base (as an attribute name)</h3>
<p>
denotes an attribute whose value
provides a URI to be used as the base for interpreting any
relative URIs in the scope of the element on which it
appears; its value is inherited. This name is reserved
by virtue of its definition in the XML Base specification.</p>
<p>
See <a
href="http://www.w3.org/TR/xmlbase/">http://www.w3.org/TR/xmlbase/</a>
for information about this attribute.
</p>
</div>
</xs:documentation>
</xs:annotation>
</xs:attribute>
<xs:attribute name="id" type="xs:ID">
<xs:annotation>
<xs:documentation>
<div>
<h3>id (as an attribute name)</h3>
<p>
denotes an attribute whose value
should be interpreted as if declared to be of type ID.
This name is reserved by virtue of its definition in the
xml:id specification.</p>
<p>
See <a
href="http://www.w3.org/TR/xml-id/">http://www.w3.org/TR/xml-id/</a>
for information about this attribute.
</p>
</div>
</xs:documentation>
</xs:annotation>
</xs:attribute>
<xs:attributeGroup name="specialAttrs">
<xs:attribute ref="xml:base"/>
<xs:attribute ref="xml:lang"/>
<xs:attribute ref="xml:space"/>
<xs:attribute ref="xml:id"/>
</xs:attributeGroup>
<xs:annotation>
<xs:documentation>
<div>
<h3>Father (in any context at all)</h3>
<div class="bodytext">
<p>
denotes Jon Bosak, the chair of
the original XML Working Group. This name is reserved by
the following decision of the W3C XML Plenary and
XML Coordination groups:
</p>
<blockquote>
<p>
In appreciation for his vision, leadership and
dedication the W3C XML Plenary on this 10th day of
February, 2000, reserves for Jon Bosak in perpetuity
the XML name "xml:Father".
</p>
</blockquote>
</div>
</div>
</xs:documentation>
</xs:annotation>
<xs:annotation>
<xs:documentation>
<div xml:id="usage" id="usage">
<h2><a name="usage">About this schema document</a></h2>
<div class="bodytext">
<p>
This schema defines attributes and an attribute group suitable
for use by schemas wishing to allow <code>xml:base</code>,
<code>xml:lang</code>, <code>xml:space</code> or
<code>xml:id</code> attributes on elements they define.
</p>
<p>
To enable this, such a schema must import this schema for
the XML namespace, e.g. as follows:
</p>
<pre>
&lt;schema . . .>
. . .
&lt;import namespace="http://www.w3.org/XML/1998/namespace"
schemaLocation="http://www.w3.org/2001/xml.xsd"/>
</pre>
<p>
or
</p>
<pre>
&lt;import namespace="http://www.w3.org/XML/1998/namespace"
schemaLocation="http://www.w3.org/2009/01/xml.xsd"/>
</pre>
<p>
Subsequently, qualified reference to any of the attributes or the
group defined below will have the desired effect, e.g.
</p>
<pre>
&lt;type . . .>
. . .
&lt;attributeGroup ref="xml:specialAttrs"/>
</pre>
<p>
will define a type which will schema-validate an instance element
with any of those attributes.
</p>
</div>
</div>
</xs:documentation>
</xs:annotation>
<xs:annotation>
<xs:documentation>
<div id="nsversioning" xml:id="nsversioning">
<h2><a name="nsversioning">Versioning policy for this schema document</a></h2>
<div class="bodytext">
<p>
In keeping with the XML Schema WG's standard versioning
policy, this schema document will persist at
<a href="http://www.w3.org/2009/01/xml.xsd">
http://www.w3.org/2009/01/xml.xsd</a>.
</p>
<p>
At the date of issue it can also be found at
<a href="http://www.w3.org/2001/xml.xsd">
http://www.w3.org/2001/xml.xsd</a>.
</p>
<p>
The schema document at that URI may however change in the future,
in order to remain compatible with the latest version of XML
Schema itself, or with the XML namespace itself. In other words,
if the XML Schema or XML namespaces change, the version of this
document at <a href="http://www.w3.org/2001/xml.xsd">
http://www.w3.org/2001/xml.xsd
</a>
will change accordingly; the version at
<a href="http://www.w3.org/2009/01/xml.xsd">
http://www.w3.org/2009/01/xml.xsd
</a>
will not change.
</p>
<p>
Previous dated (and unchanging) versions of this schema
document are at:
</p>
<ul>
<li><a href="http://www.w3.org/2009/01/xml.xsd">
http://www.w3.org/2009/01/xml.xsd</a></li>
<li><a href="http://www.w3.org/2007/08/xml.xsd">
http://www.w3.org/2007/08/xml.xsd</a></li>
<li><a href="http://www.w3.org/2004/10/xml.xsd">
http://www.w3.org/2004/10/xml.xsd</a></li>
<li><a href="http://www.w3.org/2001/03/xml.xsd">
http://www.w3.org/2001/03/xml.xsd</a></li>
</ul>
</div>
</div>
</xs:documentation>
</xs:annotation>
</xs:schema>
+43 -43
View File
@@ -399,47 +399,47 @@ Arquivar para si é uma coisa; republicar é outra.
## 9. Descrição arquivística (NOBRADE)
Resumo da norma e decisões de aplicação em [`CONARQ.md`](../CONARQ.md).
Implementação no branch `feat/nobrade`.
Implementação no branch `feat/nobrade`: `cd pipeline && python3 -m nobrade && python3 -m nobrade.mural`.
| # | Tarefa | Entrega | Depende de |
|---|---|---|---|
| **0 — Decisões** ||||
| 0.1 | Definir nome da entidade custodiadora e código provisório (`BR XYZ`) | `pipeline/nobrade/config.py` | — |
| 0.2 | Pedir código de entidade ao CONARQ | e-mail enviado | 0.1 |
| 0.3 | Fixar a convenção do código de referência (`BR XYZ BF.IMS.GF.12345`) | `CONARQ.md` §5.2 | 0.1 |
| **1 — Normalizadores (cada um gera uma tabela de revisão)** ||||
| 1.1 | Datas: mais de 20 formatos de `dc.date` → forma NOBRADE (`[1860?]`, `[18--]`) + ISO 8601 + original | `descricao/revisao/datas.tsv` | — |
| 1.2 | Atribuir data aproximada aos `s.d.` a partir do fotógrafo | coluna em `datas.tsv` | 1.1, 1.4 |
| 1.3 | Séries: 2.657 combinações de `dc.source` → séries canônicas por instituição | `descricao/revisao/series.tsv` | — |
| 1.4 | Autoridades: fotógrafos (`dc.contributor`) e colecionadores, com variantes deduplicadas | `descricao/autoridades.jsonl` | — |
| 1.5 | Suporte/espécie: `dc.type` → gênero + espécie + suporte | `descricao/revisao/tipos.tsv` | — |
| 1.6 | Direitos: `dc.rights` → ~4 categorias, mantendo o original | `descricao/revisao/direitos.tsv` | — |
| 1.7 | Data tópica: `dc.coverage` → cidade (UF) | campo 1.3 | — |
| 1.8 | Assuntos: `dc.subject` separado em pt/en | campo 8.1 | — |
| **2 — Montagem da hierarquia** ||||
| 2.1 | `nobrade`: níveis 0→5 com `id`, `parent_id`, `nivel`, `codigo` | `descricao/unidades.jsonl` | 0.3, 1.3 |
| 2.2 | Preencher os elementos por nível a partir dos normalizadores | campos `"1.3"`, `"2.1"`… | 1.x, 2.1 |
| 2.3 | Nível 5 para os handles com várias imagens | registros filhos | 2.1 |
| 2.4 | Somar dimensão e suporte nos níveis 1–3 | campo 1.5 agregado | 2.2 |
| **3 — Textos dos níveis altos** ||||
| 3.1 | Nível 1: história arquivística, procedência, acesso, arranjo | `descricao/textos/nivel1.md` | — |
| 3.2 | Nível 2: breve histórico das 16 instituições | `descricao/textos/secoes/` | — |
| 3.3 | Nível 3: âmbito e conteúdo das séries principais | `descricao/textos/series/` | 1.3 |
| 3.4 | Biografias de fotógrafos a partir dos posts do WordPress | campo 2.2 das autoridades | 1.4 |
| **4 — Relações e fontes** ||||
| 4.1 | 5.1 Originais: instituição + handle + Sophia + objdigital | campo automático | 2.1 |
| 4.2 | 5.2 Cópias: preservação, legado, miniaturas no S3 | campo automático | 2.1 |
| 4.3 | 5.4 Publicações: posts do WordPress → handles citados | campo 5.4 | — |
| **5 — Validação** ||||
| 5.1 | Validador dos 7 obrigatórios por nível | `descricao/pendencias.md` | 2.x |
| 5.2 | Rodar, corrigir e repetir até zerar as pendências | relatório limpo | 5.1 |
| **6 — Exportação e publicação** ||||
| 6.1 | Exportar EAD 3 | `descricao/ead/brasiliana.xml` | 5.2 |
| 6.2 | Exportar EAC-CPF | `descricao/eac/*.xml` | 1.4 |
| 6.3 | Validar contra os XSD | xmllint limpo | 6.1, 6.2 |
| 6.4 | Subir `descricao/` para `s3://brasiliana/descricao/` e atualizar o MANIFEST | objetos no bucket | 6.3 |
| 6.5 | (opcional) CSV de importação do AtoM | `descricao/atom.csv` | 5.2 |
| **7 — Mural** ||||
| 7.1 | Cartão com código de referência, data normalizada, suporte, "original em" | `web/wall.html` | 2.2 |
| 7.2 | Filtro por série (nível 3) | `web/wall.html` | 1.3 |
| 7.3 | Publicar em `xyz/brasiliana` | commit | 7.x |
| # | Tarefa | Entrega | Depende de | Estado |
|---|---|---|---|---|
| **0 — Decisões** |||||
| 0.1 | Definir nome da entidade custodiadora e código provisório (`BR RJXYZ`) | `pipeline/nobrade/config.py` | — | ✅ provisório `BR RJXYZ` |
| 0.2 | Pedir código de entidade ao CONARQ | e-mail enviado | 0.1 | ⏳ depende de você |
| 0.3 | Fixar a convenção do código de referência (`BR RJXYZ.BF.IMS.GF.12345.01`) | `CONARQ.md` §5.2 | 0.1 | ✅ |
| **1 — Normalizadores (cada um gera uma tabela de revisão)** |||||
| 1.1 | Datas: mais de 20 formatos de `dc.date` → forma NOBRADE (`[1860?]`, `[18--]`) + ISO 8601 + original | `descricao/revisao/datas.tsv` | — | ✅ |
| 1.2 | Atribuir data aproximada aos `s.d.` a partir do fotógrafo | coluna em `datas.tsv` | 1.1, 1.4 | ✅ |
| 1.3 | Séries: 2.657 combinações de `dc.source` → séries canônicas por instituição | `descricao/revisao/series.tsv` | — | ✅ |
| 1.4 | Autoridades: fotógrafos (`dc.contributor`) e colecionadores, com variantes deduplicadas | `descricao/autoridades.jsonl` | — | ✅ |
| 1.5 | Suporte/espécie: `dc.type` → gênero + espécie + suporte | `descricao/revisao/tipos.tsv` | — | ✅ |
| 1.6 | Direitos: `dc.rights` → ~4 categorias, mantendo o original | `descricao/revisao/direitos.tsv` | — | ✅ |
| 1.7 | Data tópica: `dc.coverage` → cidade (UF) | campo 1.3 | — | ✅ |
| 1.8 | Assuntos: `dc.subject` separado em pt/en | campo 8.1 | — | ✅ |
| **2 — Montagem da hierarquia** |||||
| 2.1 | `nobrade`: níveis 0→5 com `id`, `parent_id`, `nivel`, `codigo` | `descricao/unidades.jsonl` | 0.3, 1.3 | ✅ |
| 2.2 | Preencher os elementos por nível a partir dos normalizadores | campos `"1.3"`, `"2.1"`… | 1.x, 2.1 | ✅ |
| 2.3 | Nível 5 para os handles com várias imagens | registros filhos | 2.1 | ✅ toda imagem é nível 5 |
| 2.4 | Somar dimensão e suporte nos níveis 1–3 | campo 1.5 agregado | 2.2 | ✅ |
| **3 — Textos dos níveis altos** |||||
| 3.1 | Nível 1: história arquivística, procedência, acesso, arranjo | `descricao/textos/nivel1.md` | — | ✅ |
| 3.2 | Nível 2: breve histórico das 16 instituições | `descricao/textos/secoes/` | — | 📝 rascunho |
| 3.3 | Nível 3: âmbito e conteúdo das séries principais | `descricao/textos/series/` | 1.3 | ✅ resumo automático |
| 3.4 | Biografias de fotógrafos a partir dos posts do WordPress | campo 2.2 das autoridades | 1.4 | ✅ fontes nas autoridades |
| **4 — Relações e fontes** |||||
| 4.1 | 5.1 Originais: instituição + handle + Sophia + objdigital | campo automático | 2.1 | ✅ |
| 4.2 | 5.2 Cópias: preservação, legado, miniaturas no S3 | campo automático | 2.1 | ✅ |
| 4.3 | 5.4 Publicações: posts do WordPress → handles citados | campo 5.4 | — | ✅ |
| **5 — Validação** |||||
| 5.1 | Validador dos 7 obrigatórios por nível | `descricao/pendencias.md` | 2.x | ✅ |
| 5.2 | Rodar, corrigir e repetir até zerar as pendências | relatório limpo | 5.1 | ✅ 0 pendências |
| **6 — Exportação e publicação** |||||
| 6.1 | Exportar EAD 3 | `descricao/ead/brasiliana.xml` | 5.2 | ✅ valida |
| 6.2 | Exportar EAC-CPF | `descricao/eac/*.xml` | 1.4 | ✅ valida |
| 6.3 | Validar contra os XSD | xmllint limpo | 6.1, 6.2 | ✅ |
| 6.4 | Subir `descricao/` para `s3://brasiliana/descricao/` e atualizar o MANIFEST | objetos no bucket | 6.3 | ⏳ aguardando ok |
| 6.5 | (opcional) CSV de importação do AtoM | `descricao/atom.csv` | 5.2 | ✅ |
| **7 — Mural** |||||
| 7.1 | Cartão com código de referência, data normalizada, suporte, "original em" | `web/wall.html` | 2.2 | ✅ |
| 7.2 | Filtro por série (nível 3) | `web/wall.html` | 1.3 | ✅ |
| 7.3 | Publicar em `xyz/brasiliana` | commit | 7.x | ⏳ aguardando ok |
File diff suppressed because one or more lines are too long
+38 -12
View File
@@ -426,6 +426,8 @@
#card-footer a { color: #d8b04a; text-decoration: none; }
#card-footer a:hover { text-decoration: underline; }
#card-rights { margin-top: 6px; font-size: .68rem; color: #777; }
#card-ref { font: .7rem/1.3 ui-monospace, SFMono-Regular, Menlo, monospace; color: #8a8a82; margin-top: 4px; }
#card-ref .serie { font-family: system-ui, -apple-system, sans-serif; letter-spacing: .02em; }
/* stepping between pieces without a keyboard */
#card-nav { display: flex; gap: 9px; margin-top: 16px; }
@@ -635,6 +637,10 @@
<label for="f-colecao">Coleção</label>
<select id="f-colecao"><option value="">todas</option></select>
</div>
<div class="f-row">
<label for="f-serie">Série (arranjo NOBRADE)</label>
<select id="f-serie"><option value="">todas</option></select>
</div>
<div class="f-row">
<label for="f-pessoa">Pessoa</label>
<select id="f-pessoa"><option value="">todas</option></select>
@@ -660,6 +666,7 @@
<div id="card-img-wrap"><img id="card-img" alt=""></div>
<div id="card-title">—</div>
<div id="card-date">—</div>
<div id="card-ref"></div>
<div id="card-contrib"></div>
<div id="card-tags"></div>
<div id="card-related" hidden></div>
@@ -1063,6 +1070,7 @@ renderer.domElement.addEventListener('pointermove', e => {
// (the "hole" always opens in the middle, wherever you clicked).
let atlasSources = []; // { source, size } per atlas page — used to crop the tile into the card canvas
let atlasEntries = null, TPR = 1;
let seriesTitles = []; // títulos das séries NOBRADE (nível 3); meta.si indexa aqui
let selected = null;
let selectedAt = 0;
@@ -1393,11 +1401,20 @@ function tileThumbUrl(handle, px) {
function showCard(data) {
const meta = data.meta || {};
document.getElementById('card-type').textContent = meta.type || 'Fotografia';
document.getElementById('card-type').textContent = meta.sup || meta.type || 'Fotografia';
document.getElementById('card-community').textContent = meta.community || '—';
document.getElementById('card-date-tag').textContent = prettyDate(meta.date) || 's.d.';
document.getElementById('card-date-tag').textContent = meta.dt || prettyDate(meta.date) || 's.d.';
document.getElementById('card-title').textContent = meta.title || '(sem título)';
document.getElementById('card-date').textContent = prettyDate(meta.date);
document.getElementById('card-date').textContent = meta.dt || prettyDate(meta.date);
// código de referência NOBRADE e a série (nível 3) a que a peça pertence
const refEl = document.getElementById('card-ref');
refEl.textContent = meta.ref || '';
if (meta.si != null && seriesTitles[meta.si]) {
const sr = document.createElement('div');
sr.className = 'serie';
sr.textContent = seriesTitles[meta.si];
refEl.appendChild(sr);
}
document.getElementById('card-contrib').textContent = meta.contributor ? meta.contributor : '';
// this piece's dc.subject, one chip each (accent/case duplicates folded)
const tagsEl = document.getElementById('card-tags');
@@ -1406,7 +1423,8 @@ function showCard(data) {
renderRelated(data);
document.getElementById('card-handle').textContent = data.handle || '';
document.getElementById('card-link').href = data.handle ? sourceUrl(data.handle) : '#';
document.getElementById('card-rights').textContent = meta.rights ? `Direitos: ${meta.rights}` : '';
document.getElementById('card-rights').textContent =
[meta.rep && meta.rep[0].toUpperCase() + meta.rep.slice(1), meta.rights && `Direitos: ${meta.rights}`].filter(Boolean).join(' · ');
// crop this tile out of the atlas image for a (still small, but framed) preview
const entry = atlasEntries[data.handle];
@@ -1493,6 +1511,7 @@ function flattenMeta(value) {
}
function yearOf(meta) {
if (meta && Number.isInteger(meta.ano)) return meta.ano;
const m = String((meta || {}).date || '').match(/(1[5-9]\d{2}|20\d{2})/);
return m ? parseInt(m[1], 10) : null;
}
@@ -1961,6 +1980,7 @@ function setupFilters(mapData) {
const a = cleanAuthor(meta.contributor);
m.userData._author = a ? authorKey(a) : '';
m.userData._type = cleanType(meta.type);
m.userData._serie = meta.si != null ? seriesTitles[meta.si] || '' : '';
Object.assign(m.userData, (({ st, ct, bh, tp, col, pes }) => ({ _st: st, _ct: ct, _bh: bh, _tp: tp, _col: col, _pes: pes }))(subjectFacets(meta)));
// one haystack per piece: every metadata field, not a chosen few
// the handle is the map's key, not a field of meta — it still has to be
@@ -1992,6 +2012,7 @@ function setupFilters(mapData) {
const selTopico = document.getElementById('f-topico');
const selColecao = document.getElementById('f-colecao');
const selPessoa = document.getElementById('f-pessoa');
const selSerie = document.getElementById('f-serie');
const fillSelect = (sel, rows, first) => {
sel.replaceChildren(Object.assign(document.createElement('option'), { value: '', textContent: first }));
rows.forEach(([value, n]) => {
@@ -2036,7 +2057,7 @@ function setupFilters(mapData) {
sel.value = value;
}
const state = { search: '', institution: '', yearLo: decadeMin, yearHi: decadeMax, yearTouched: false, author: '', type: '', estado: '', cidade: '', bairro: '', topico: '', colecao: '', pessoa: '' };
const state = { search: '', institution: '', yearLo: decadeMin, yearHi: decadeMax, yearTouched: false, author: '', type: '', estado: '', cidade: '', bairro: '', topico: '', colecao: '', pessoa: '', serie: '' };
function resetYear() {
state.yearTouched = false;
@@ -2064,6 +2085,7 @@ function setupFilters(mapData) {
(!state.topico || d._tp.has(topicPrefix() + state.topico)) &&
(!state.colecao || d._col.has(state.colecao)) &&
(!state.pessoa || d._pes.has(state.pessoa)) &&
(!state.serie || d._serie === state.serie) &&
terms.every(t => d._hay.includes(t));
if (okRest && d._year != null) {
const i = Math.floor((d._year - decadeMin) / 10);
@@ -2131,6 +2153,7 @@ function setupFilters(mapData) {
if (state.topico) out.push({ key: 'topico', text: state.topico });
if (state.colecao) out.push({ key: 'colecao', text: state.colecao });
if (state.pessoa) out.push({ key: 'pessoa', text: state.pessoa });
if (state.serie) out.push({ key: 'serie', text: state.serie });
if (state.type) out.push({ key: 'type', text: state.type });
return out;
}
@@ -2145,6 +2168,7 @@ function setupFilters(mapData) {
if (key === 'topico') { state.topico = ''; selTopico.value = ''; }
if (key === 'colecao') { state.colecao = ''; selColecao.value = ''; }
if (key === 'pessoa') { state.pessoa = ''; selPessoa.value = ''; }
if (key === 'serie') { state.serie = ''; selSerie.value = ''; }
if (key === 'author') { state.author = ''; selAuthor.value = ''; }
if (key === 'year') resetYear();
apply();
@@ -2192,6 +2216,7 @@ function setupFilters(mapData) {
selTopico.addEventListener('change', () => { state.topico = selTopico.value; apply(); });
selColecao.addEventListener('change', () => { state.colecao = selColecao.value; apply(); });
selPessoa.addEventListener('change', () => { state.pessoa = selPessoa.value; apply(); });
selSerie.addEventListener('change', () => { state.serie = selSerie.value; apply(); });
selAuthor.addEventListener('change', () => { state.author = selAuthor.value; apply(); });
function onYear(e) {
@@ -2211,8 +2236,8 @@ function setupFilters(mapData) {
clearBtn.addEventListener('click', () => {
clearTimeout(searchTimer);
state.search = ''; state.institution = ''; state.type = ''; state.author = ''; state.estado = state.cidade = state.bairro = state.topico = state.colecao = state.pessoa = '';
searchInput.value = ''; selInst.value = ''; selType.value = ''; selAuthor.value = ''; selEstado.value = ''; selColecao.value = ''; selPessoa.value = ''; rebuildPlace();
state.search = ''; state.institution = ''; state.type = ''; state.author = ''; state.estado = state.cidade = state.bairro = state.topico = state.colecao = state.pessoa = state.serie = '';
searchInput.value = ''; selInst.value = ''; selType.value = ''; selAuthor.value = ''; selEstado.value = ''; selColecao.value = ''; selPessoa.value = ''; selSerie.value = ''; rebuildPlace();
resetYear();
apply();
});
@@ -2220,13 +2245,14 @@ function setupFilters(mapData) {
fillSelect(selEstado, tally('', d => d._st, 1), 'todos');
fillSelect(selColecao, tally('', d => d._col, 1), 'todas');
fillSelect(selPessoa, tally('', d => d._pes, 5), 'todas');
fillSelect(selSerie, tally('', d => d._serie ? [d._serie] : [], 1), 'todas');
// a tag on the card applies itself as a filter; the URL carries the filters
// (?estado=…&topico=…) so a filtered wall can be shared and survives a reload
const URL_KEYS = { q: 'search', inst: 'institution', autor: 'author', tipo: 'type', estado: 'estado', cidade: 'cidade',
bairro: 'bairro', topico: 'topico', colecao: 'colecao', pessoa: 'pessoa' };
bairro: 'bairro', topico: 'topico', colecao: 'colecao', pessoa: 'pessoa', serie: 'serie' };
const SELECTS = { institution: selInst, author: selAuthor, type: selType, estado: selEstado, cidade: selCidade,
bairro: selBairro, topico: selTopico, colecao: selColecao, pessoa: selPessoa };
bairro: selBairro, topico: selTopico, colecao: selColecao, pessoa: selPessoa, serie: selSerie };
function syncUrl() {
const p = new URLSearchParams();
Object.entries(URL_KEYS).forEach(([k, f]) => { if (state[f]) p.set(k, state[f]); });
@@ -2326,6 +2352,7 @@ async function main() {
const mapData = JSON.parse(await catalogue.blob.text());
TPR = mapData.size / mapData.tile;
atlasEntries = mapData.map;
seriesTitles = mapData.series || [];
const handles = Object.keys(mapData.map);
// the note only earns its space in placeholder mode — the piece count already
@@ -2342,9 +2369,8 @@ async function main() {
for (const entry of Object.values(mapData.map)) {
const meta = entry.meta || {};
if (meta.community) institutions.add(meta.community);
const m = String(meta.date || '').match(/(1[5-9]\d{2}|20\d{2})/);
if (m) {
const y = parseInt(m[1], 10);
const y = yearOf(meta);
if (y != null) {
if (y < minYear) minYear = y;
if (y > maxYear) maxYear = y;
}