diff --git a/go.mod b/go.mod
index 2e6e29ba..41b8bf5a 100644
--- a/go.mod
+++ b/go.mod
@@ -3,6 +3,7 @@ module github.com/artefactual-sdps/preprocessing-sfa
go 1.23.2
require (
+ github.com/antchfx/xmlquery v1.4.2
github.com/artefactual-sdps/temporal-activities v0.0.0-20241018212855-8ea34d29bdf4
github.com/beevik/etree v1.4.0
github.com/deckarep/golang-set/v2 v2.6.0
@@ -23,6 +24,7 @@ require (
)
require (
+ github.com/antchfx/xpath v1.3.2 // indirect
github.com/aws/aws-sdk-go v1.55.5 // indirect
github.com/aws/aws-sdk-go-v2 v1.30.3 // indirect
github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.6.3 // indirect
diff --git a/go.sum b/go.sum
index 7ab41d85..7f102ac9 100644
--- a/go.sum
+++ b/go.sum
@@ -13,6 +13,10 @@ cloud.google.com/go/iam v1.1.13/go.mod h1:K8mY0uSXwEXS30KrnVb+j54LB/ntfZu1dr+4zF
cloud.google.com/go/storage v1.43.0 h1:CcxnSohZwizt4LCzQHWvBf1/kvtHUn7gk9QERXPyXFs=
cloud.google.com/go/storage v1.43.0/go.mod h1:ajvxEa7WmZS1PxvKRq4bq0tFT3vMd502JwstCcYv0Q0=
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
+github.com/antchfx/xmlquery v1.4.2 h1:MZKd9+wblwxfQ1zd1AdrTsqVaMjMCwow3IqkCSe00KA=
+github.com/antchfx/xmlquery v1.4.2/go.mod h1:QXhvf5ldTuGqhd1SHNvvtlhhdQLks4dD0awIVhXIDTA=
+github.com/antchfx/xpath v1.3.2 h1:LNjzlsSjinu3bQpw9hWMY9ocB80oLOWuQqFvO6xt51U=
+github.com/antchfx/xpath v1.3.2/go.mod h1:i54GszH55fYfBmoZXapTHN8T8tkcHfRgLyVwwqzXNcs=
github.com/artefactual-sdps/temporal-activities v0.0.0-20241018212855-8ea34d29bdf4 h1:WF95IOkZRVSCST/26SAqPYsUrtUuJpavBht6lvdeKl0=
github.com/artefactual-sdps/temporal-activities v0.0.0-20241018212855-8ea34d29bdf4/go.mod h1:FVh79rCGNlUU1QnioAU+lrSjLqrA1PJFYKIhWPsmyug=
github.com/aws/aws-sdk-go v1.55.5 h1:KKUZBfBoyqy5d3swXyiC7Q76ic40rYcbqH7qjh59kzU=
@@ -307,6 +311,7 @@ golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
+golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
golang.org/x/net v0.15.0/go.mod h1:idbUs1IY1+zTqbi8yxTbhexhEEk5ur9LInksu6HrEpk=
golang.org/x/net v0.20.0/go.mod h1:z8BVo6PvndSri0LbOE3hAn0apkU+1YvI6E70E9jsnvY=
diff --git a/internal/ais/combinemd.go b/internal/ais/combinemd.go
new file mode 100644
index 00000000..ca33b36d
--- /dev/null
+++ b/internal/ais/combinemd.go
@@ -0,0 +1,120 @@
+package ais
+
+import (
+ "context"
+ "fmt"
+ "io"
+ "os"
+ "path/filepath"
+ "strings"
+
+ "github.com/antchfx/xmlquery"
+
+ "github.com/artefactual-sdps/preprocessing-sfa/internal/fsutil"
+)
+
+const CombineMDActivityName = "combine-metadata-files"
+
+type (
+ CombineMDActivity struct{}
+ CombineMDActivityParams struct {
+ AreldaRelPath string
+ METSRelPath string
+ WorkingDir string
+ }
+ CombineMDActivityResult struct {
+ Path string
+ }
+)
+
+func NewCombineMDActivity() *CombineMDActivity {
+ return &CombineMDActivity{}
+}
+
+func (a *CombineMDActivity) Execute(ctx context.Context, params CombineMDActivityParams) (*CombineMDActivityResult, error) {
+ areldaPath := filepath.Join(params.WorkingDir, params.AreldaRelPath)
+ if !fsutil.FileExists(areldaPath) {
+ return nil, fmt.Errorf("missing Arelda file: %s", areldaPath)
+ }
+
+ metsPath := filepath.Join(params.WorkingDir, params.METSRelPath)
+ if !fsutil.FileExists(metsPath) {
+ return nil, fmt.Errorf("missing METS file: %s", metsPath)
+ }
+
+ aisName, err := aisFilename(areldaPath)
+ if err != nil {
+ return nil, fmt.Errorf("name AIS file: %v", err)
+ }
+
+ dest := filepath.Join(params.WorkingDir, aisName)
+
+ f, err := os.Create(dest)
+ if err != nil {
+ return nil, fmt.Errorf("create AIS file: %v", err)
+ }
+ f.Close()
+
+ if err = fappend(dest, filepath.Join(params.WorkingDir, params.AreldaRelPath)); err != nil {
+ return nil, fmt.Errorf("append Arelda metadata: %v", err)
+ }
+
+ if err = fappend(dest, filepath.Join(params.WorkingDir, params.METSRelPath)); err != nil {
+ return nil, fmt.Errorf("append METS metadata: %v", err)
+ }
+
+ return &CombineMDActivityResult{Path: dest}, nil
+}
+
+func aisFilename(mdpath string) (string, error) {
+ id, err := parseAccessionID(mdpath)
+ if err != nil {
+ return "", fmt.Errorf("get accession number: %v", err)
+ }
+
+ id = strings.ReplaceAll(id, "/", "_")
+
+ return fmt.Sprintf("AIS_%s", id), nil
+}
+
+func parseAccessionID(path string) (string, error) {
+ f, err := os.Open(path) // #nosec G304 -- trusted path
+ if err != nil {
+ return "", fmt.Errorf("open metadata file: %v", err)
+ }
+ defer f.Close()
+
+ sp, err := xmlquery.CreateStreamParser(f, "//paket/ablieferung/ablieferungsnummer")
+ if err != nil {
+ return "", fmt.Errorf("create XML parser: %v", err)
+ }
+
+ n, err := sp.Read()
+ if err == io.EOF {
+ return "", fmt.Errorf("can't find ablieferungsnummer in %q", filepath.Base(path))
+ }
+ if err != nil {
+ return "", fmt.Errorf("read XML stream: %v", err)
+ }
+ return n.InnerText(), nil
+}
+
+func fappend(dest, src string) error {
+ r, err := os.Open(src)
+ if err != nil {
+ return fmt.Errorf("open src: %v", err)
+ }
+ defer r.Close()
+
+ w, err := os.OpenFile(dest, os.O_WRONLY|os.O_APPEND, os.FileMode(0o666))
+ if err != nil {
+ return fmt.Errorf("open dest: %v", err)
+ }
+ defer r.Close()
+
+ if _, err = io.Copy(w, r); err != nil {
+ return fmt.Errorf("copy: %v", err)
+ }
+
+ return nil
+}
diff --git a/internal/ais/combinemd_test.go b/internal/ais/combinemd_test.go
new file mode 100644
index 00000000..d4e1278b
--- /dev/null
+++ b/internal/ais/combinemd_test.go
@@ -0,0 +1,123 @@
+package ais_test
+
+import (
+ "strings"
+ "testing"
+
+ temporalsdk_activity "go.temporal.io/sdk/activity"
+ temporalsdk_testsuite "go.temporal.io/sdk/testsuite"
+ "gotest.tools/v3/assert"
+ "gotest.tools/v3/fs"
+
+ "github.com/artefactual-sdps/preprocessing-sfa/internal/ais"
+)
+
+const (
+ mets = `
+
+
+`
+
+ arelda = `
+
+
+
+ FILES
+ Bundesverwaltung (Bern)
+ 1000/893_3251903
+
+
+`
+)
+
+func testDir(t *testing.T) string {
+ td := fs.NewDir(t, "ppsfa",
+ fs.WithFile("arelda.xml", arelda),
+ fs.WithFile("mets.xml", mets),
+ )
+
+ return td.Path()
+}
+
+func TestExecute(t *testing.T) {
+ t.Parallel()
+
+ tests := []struct {
+ name string
+ params ais.CombineMDActivityParams
+ want ais.CombineMDActivityResult
+ wantErr string
+ }{
+ {
+ name: "Returns the combined metadata",
+ params: ais.CombineMDActivityParams{
+ AreldaRelPath: "arelda.xml",
+ METSRelPath: "mets.xml",
+ WorkingDir: testDir(t),
+ },
+ want: ais.CombineMDActivityResult{Path: "{{wd}}/AIS_1000_893_3251903"},
+ },
+ {
+ name: "Errors if the Arelda file doesn't exist",
+ params: ais.CombineMDActivityParams{
+ AreldaRelPath: "missing.xml",
+ WorkingDir: testDir(t),
+ },
+ wantErr: "activity error (type: combine-metadata-files, scheduledEventID: 0, startedEventID: 0, identity: ): missing Arelda file: {{wd}}/missing.xml",
+ },
+ {
+ name: "Errors if the METS file doesn't exist",
+ params: ais.CombineMDActivityParams{
+ AreldaRelPath: "arelda.xml",
+ METSRelPath: "missing.xml",
+ WorkingDir: testDir(t),
+ },
+ wantErr: "activity error (type: combine-metadata-files, scheduledEventID: 0, startedEventID: 0, identity: ): missing METS file: {{wd}}/missing.xml",
+ },
+ {
+ name: "Errors when the Arelda file is invalid",
+ params: ais.CombineMDActivityParams{
+ AreldaRelPath: "mets.xml",
+ WorkingDir: testDir(t),
+ },
+ wantErr: "activity error (type: combine-metadata-files, scheduledEventID: 0, startedEventID: 0, identity: ): name AIS file: get accession number: can't find ablieferungsnummer in \"mets.xml\"",
+ },
+ }
+ for _, tt := range tests {
+ t.Run(tt.name, func(t *testing.T) {
+ t.Parallel()
+
+ ts := &temporalsdk_testsuite.WorkflowTestSuite{}
+ env := ts.NewTestActivityEnvironment()
+ env.RegisterActivityWithOptions(
+ ais.NewCombineMDActivity().Execute,
+ temporalsdk_activity.RegisterOptions{Name: ais.CombineMDActivityName},
+ )
+
+ tt.want.Path = strings.ReplaceAll(tt.want.Path, "{{wd}}", tt.params.WorkingDir)
+ tt.wantErr = strings.ReplaceAll(tt.wantErr, "{{wd}}", tt.params.WorkingDir)
+
+ future, err := env.ExecuteActivity(ais.CombineMDActivityName, tt.params)
+ if tt.wantErr != "" {
+ if err == nil {
+ t.Errorf("error is nil, expecting: %q", tt.wantErr)
+ } else {
+ assert.ErrorContains(t, err, tt.wantErr)
+ }
+
+ return
+ }
+ assert.NilError(t, err)
+
+ var got ais.CombineMDActivityResult
+ future.Get(&got)
+ assert.DeepEqual(t, got, tt.want)
+ })
+ }
+}
diff --git a/internal/ais/workflow.go b/internal/ais/workflow.go
index 351a2eed..a3b5ab15 100644
--- a/internal/ais/workflow.go
+++ b/internal/ais/workflow.go
@@ -151,36 +151,25 @@ func (w *Workflow) SessionHandler(ctx temporalsdk_workflow.Context, params *Work
return "", e
}
+ var metadataPath string
if parseResult.UpdatedAreldaMetadataRelPath != "" {
- var fetchMetadataResult FetchActivityResult
- e = temporalsdk_workflow.ExecuteActivity(
- withRemoteActOpts(ctx),
- FetchActivityName,
- &FetchActivityParams{
- AIPUUID: params.AIPUUID,
- RelativePath: fmt.Sprintf("%s/data/%s", aipDirName, parseResult.UpdatedAreldaMetadataRelPath),
- Destination: filepath.Join(localDir, filepath.Base(parseResult.UpdatedAreldaMetadataRelPath)),
- },
- ).Get(ctx, &fetchMetadataResult)
- if e != nil {
- return "", e
- }
+ metadataPath = parseResult.UpdatedAreldaMetadataRelPath
+ } else {
+ metadataPath = parseResult.MetadataRelPath
}
- if parseResult.UpdatedAreldaMetadataRelPath == "" && parseResult.MetadataRelPath != "" {
- var fetchMetadataResult FetchActivityResult
- e = temporalsdk_workflow.ExecuteActivity(
- withRemoteActOpts(ctx),
- FetchActivityName,
- &FetchActivityParams{
- AIPUUID: params.AIPUUID,
- RelativePath: fmt.Sprintf("%s/data/%s", aipDirName, parseResult.MetadataRelPath),
- Destination: filepath.Join(localDir, filepath.Base(parseResult.MetadataRelPath)),
- },
- ).Get(ctx, &fetchMetadataResult)
- if e != nil {
- return "", e
- }
+ var fetchMetadataResult FetchActivityResult
+ e = temporalsdk_workflow.ExecuteActivity(
+ withRemoteActOpts(ctx),
+ FetchActivityName,
+ &FetchActivityParams{
+ AIPUUID: params.AIPUUID,
+ RelativePath: fmt.Sprintf("%s/data/%s", aipDirName, metadataPath),
+ Destination: filepath.Join(localDir, filepath.Base(metadataPath)),
+ },
+ ).Get(ctx, &fetchMetadataResult)
+ if e != nil {
+ return "", e
}
var zipResult archivezip.Result
diff --git a/internal/testdata/little-Test-AIP-Digitization/AIS_1000_893_3251903 b/internal/testdata/little-Test-AIP-Digitization/AIS_1000_893_3251903
new file mode 100644
index 00000000..55212814
--- /dev/null
+++ b/internal/testdata/little-Test-AIP-Digitization/AIS_1000_893_3251903
@@ -0,0 +1,748 @@
+
+
+ AIP
+ 909c56e9-e334-4c0a-9736-f92c732149d9
+ fa5fb285-fa45-44e4-8d85-77ec1d774403
+ 1
+
+
+ header
+
+ old
+
+ SIP
+
+ metadata.xml
+ metadata.xml
+ MD5
+ 29a08a4c20e931bf91079abb6951c79e
+
+
+
+
+ xsd
+
+ ablieferung.xsd
+ ablieferung.xsd
+ MD5
+ aa1f7ad13064e1643ac85478296165af
+
+
+ archivischeNotiz.xsd
+ archivischeNotiz.xsd
+ MD5
+ 847911efbac472d0ecc6fe1e99873799
+
+
+ archivischerVorgang.xsd
+ archivischerVorgang.xsd
+ MD5
+ 4a237563fd2d40be9a9ecbf4c0bf946e
+
+
+ arelda.xsd
+ arelda.xsd
+ MD5
+ f8454632e1ebf97e0aa8d9527ce2641f
+
+
+ base.xsd
+ base.xsd
+ MD5
+ cb30854883c6d5640b0965dae5f34afd
+
+
+ datei.xsd
+ datei.xsd
+ MD5
+ a4276f0c798ce6c497f0a03660ead0d9
+
+
+ dokument.xsd
+ dokument.xsd
+ MD5
+ 721965e5224766040bf0bcd03978809e
+
+
+ dossier.xsd
+ dossier.xsd
+ MD5
+ f3f1141d95e92a291e84cfb30bb30e9a
+
+
+ ordner.xsd
+ ordner.xsd
+ MD5
+ 83e0f91d1a232c7bdd7416970844af1c
+
+
+ ordnungssystem.xsd
+ ordnungssystem.xsd
+ MD5
+ 4b64247b25362382d6c648ba8ff76ad6
+
+
+ ordnungssystemposition.xsd
+ ordnungssystemposition.xsd
+ MD5
+ 1e7f0a9b914c8baf1235740b133ec90e
+
+
+ paket.xsd
+ paket.xsd
+ MD5
+ 9920c66b7066f645390e922ba803aadb
+
+
+ provenienz.xsd
+ provenienz.xsd
+ MD5
+ 2d6dbc4665cb5169d62549dbbc3f19a7
+
+
+ zusatzDaten.xsd
+ zusatzDaten.xsd
+ MD5
+ a685887b7ad673ea2deac6f96cf3fb4f
+
+
+
+
+ content
+
+ d_0000001
+
+ 00000001_PREMIS.xml
+ 00000001_PREMIS.xml
+ MD5
+ 11f791c655cae7f4ab1dcaf613314151
+
+
+ 00000002_PREMIS.xml
+ 00000002_PREMIS.xml
+ MD5
+ 4ed338cc69d7635450b5332fb727d2d3
+
+
+ Prozess_Digitalisierung_PREMIS.xml
+ Prozess_Digitalisierung_PREMIS.xml
+ MD5
+ 8067daaa900eba6dace69572eea8f8f3
+
+
+ 00000001.jp2
+ 00000001.jp2
+ MD5
+ f7dc1f76a55cbdca0ae4a6dc8ae64644
+
+
+ 00000002.jp2
+ 00000002.jp2
+ MD5
+ 954d06be4a70c188b6b2e5fe4309fb2c
+
+
+
+
+
+ FILES
+ Bundesverwaltung (Bern)
+ 1000/893_3251903
+
+
+ Bundesverwaltung (k.A.)
+
+
+ Eisenbahnwesen
+
+ 4.
+ Privatbahnen
+
+ 4.2
+ Normalspurbahnen
+
+ 4.2.09
+ Eisenbahnlinien Kanton Luzern
+
+ 4.2.09.12
+ Rigibahnen (Vitznau-Rigistaffel-Rigibahn)
+
+ Beschwerde von Pfyffer-Zimmermann aus Witznau und Zurücknahme derselbigen
+ digital
+
+
+
+
+
+ 1874-04-01
+
+
+
+ 1874-11-30
+
+
+
+ U_m_s_c_h_l_a_g_0000001
+ digital
+
+
+ 000001
+
+ _miEf29GTkFR7ymi91IV4fO
+ _SRpeVgb4xGImymb23OH1od
+ _mOXw3hINt3zY6WvKQOfYmk
+ _MKhAIC639MxzyOn8ji3tN5
+ _chYnT1OupaVua05V679qUi
+ _W4d0itDv1Grd0LDFAhwlmR
+ _vUbY87XIyeGLjNG5y3xndZ
+ _XUSIau5otTTxuIfouqUhn4
+ _Qau7zrpSWxttPlj5ebexFJ
+ _Gve1UlcBNTPicVrGMpwFj3
+ _AzXvLcHJZhBA9XiHtax3wL
+ _uyd7l0xiDaXnVtprqR2lQS
+
+
+ D_o_k_u_m_e_n_t_0000001
+ digital
+
+
+ 000002
+
+ _g1rji2dQsuGpZLBIaAiMPA
+ _dUXhtGwNgH35GN2YJ8pyGj
+ _m9zFkHXuktC31o11YAkQ86
+ _yeOC7WoQW2MvLRoJx9seg4
+ _vjzJldkMgFjhC2x99KxX4C
+ _sAunvZiDt97hvfFKcuUAIp
+ _c0u3TfaCacJqAVcAQA1Vgt
+ _gOPGadEspA069T2N85DpVl
+ _xEGJY9P6wMIrYF5o4mNu1j
+ _mANLal5d2ams8uKVDWrZ6u
+ _MHMqEv92PQk5OGXPz4OdVC
+ _BLhDpBCdVv7XA8lPvYXgiM
+ _kaV2BGkXL0FRUMVSOs4JtG
+ _OQaXkOBY3ZdkDOaThk115U
+ _yUdWYvrUmwzzSx9Za6oGIY
+ _ns8VmWNaaqicac23Ve41wi
+ _8hJ6bqQxfPNvZYSQNiEM0X
+ _WDOTiSst00lZpCM3sU5hCr
+ _LUdtsyL44uJOQaH6jpa6F6
+ _l6KWuZCLx1iKZ2aIB4doXK
+ _AhV2qVsjUaEYYHMqw0aAeM
+ _LqaXt7ItrSVoeFvbHDBLXQ
+ _vqe0NMPet3r3M2SceOawtc
+ _r6zP0gEmpz26iiYhh8GRG9
+ _c9YCcja1BoebFloHrpzCmj
+ _jEW3tnlvkhF2Fzx1k2YvRF
+ _65DO2vjMnsF8s822IspEQL
+ _22poW8ITNRamPDrw9WW8l7
+ _29aZ0BSA4qVep3IQg9EieM
+ _u5MaEjNn2Uz7j04gt3UnNQ
+ _CKkjeyNJ95RnEBAw0YWBno
+ _M1qm9saoSTpN75kfzVqkhg
+ _8eb0XsAYbviO9Xo3jI7U53
+ _09TwnifWryQWrjs7hScdtd
+ _Cf655IAFrvhEC8EimMn1oa
+ _Ahjio1HDqF86v9yYcrOdb7
+ _p88wAjggmlKTY2yqaLeqLO
+ _hnE15fb0ZBvcxvsM1Ma6P4
+ _1bTsyHnoHuMyaWQWXxV6Ms
+ _7YzsOEQAFlg1nigqkj1ZCg
+ _SjnRjf96WKrtNnPPZGl07Z
+ _AqJz4iIE5eqN817DBuxT0E
+ _U8ihZE3VvCx6lIiqRv5dYO
+ _bkACPSns4u8viTC5bFWGiU
+ _K16qGRbMamzTTltdDAmJAn
+ _7XoZ0Szb5fjDnKa8sxbSEG
+ _Kzy1SSowwcrK4Ek0RGTmIG
+ _GMp4D9dmzUjsZHzOcsoMpQ
+ _QUlompkdLkrAEnLg2EjoNO
+ _Uo9EciU6ILcCg65yAH47uX
+ _t2ZFRhyi8nNaNy8hQ2t4L9
+ _0D2xQ2tgEsbfv2n8701jCD
+ _RzGZcWlLHYHYHejEMtYJD1
+ _ZWFNJKDstyjzV5AY7qteck
+ _ENEIr4hcozpDvVU0lTFFNR
+ _6jkE6ZiHpLF7JsqFtHJ6Rj
+ _GF3M4aavmw3A9fj6HTvtzQ
+ _iP9W74QLwsT4iySqXWe489
+ _tCYK9lQ7Sfz1bd7hX7sbQ2
+ _r1av2rPqUUcXdCAwK38N7k
+ _34nTAWDpIsjwIRqaKzIiA9
+ _A0hWZZMTMWs0yOkVsfQIBu
+ _zIG4PT1xSfixgbIoIAiBLM
+ _WuExOQbpKcpVYiv0Zy0e6D
+ _k6oo1SW3RGkriZod3BK99p
+ _ryinWEtuwIpQNP9DyCbrbX
+ _s6EvFkDLbAvJQJNYctw0Ww
+ _tXLTqAespa6nLUIrcavkAr
+ _nwx8S8jRnOeggc1b2JFLM0
+ _9MR0mmyKTu7lD1MOmZYMXw
+ _EwRpkPdle6xkbKXFMZW3IB
+ _TgaykLwdGRzII8teYbJAEm
+ _eUK5I37sOPMxnKsWm7AEvK
+ _TYwgpiUa3dp34fWeYUnJX0
+ _u4MvnOdD3ziITgoB1U7Pzb
+ _UhXXXHpBFJu0W8w1dbvUwg
+ _xagaUMRyqSx77NnWTCyj9h
+ _IWFxD8uipl2XF44si89qdk
+ _0VKeh8UdAQ4QzTCf9DqoqU
+ _MK1pPyJ2VVKPrTmaIJ3WMu
+ _iKCifgultPZAicJf6L5Vtv
+ _mnVnAMZuJUx93XWR40mJLa
+ _4alkEjGRzdvT3zYZjmKqCU
+ _JdYHGXVQngMdqcsOQu6Ge8
+
+
+ D_o_k_u_m_e_n_t_0000002
+ digital
+
+
+ 000003
+
+ _5GbCxR3sghNXT8xA5s9HyZ
+ _TDIdElybgFikGkAIkTwqoh
+ _IMArz9cRs14LvlsMbiD8dg
+ _QqXM3KgJ6Cd5u5ZcZVLjwh
+ _HHN518svEimt6kKdODk5Hf
+ _TQiyhfZ7pij40uEWgzN9a9
+ _lW3C2jttc1YSfjb94kPsuj
+ _GZnDQZu4tttgYJ3qRnZsIw
+ _9XTvqsaQ7n0h9jnhxCNlwC
+ _T2AHO9Ay2h6xDzQxVxGIQM
+ _erkbH23XUIhY6zYvAfnflZ
+ _FCUJfG1htM4ZjL9n60SbSG
+ _iAT86o61V4mUXrVWFN8TxJ
+ _x6BXCPWfBycjT23AqKXs6z
+ _UEJcxNRFUJCwDZh1saSJL0
+ _ZXqfZ62rCifimFhGXYECU6
+ _TsE8gzpiNSIQE3KermKmIx
+ _6XU2nW1l7uO2WWFPVlb6ds
+ _Ssw46IURTviV1n60ANariT
+ _QoLTixmqRpsl8NJlijTsob
+ _zS9BqPUGf5IXNDYYrIWoK4
+ _JczB9iV7bzkO4XVPSOUhy1
+ _cypvHQeLGC4zlXrpBcfgbE
+ _xcY0O1iSB9YrBeP9dWKxaB
+ _hmBomqIVtkLqZNOLPETgEv
+ _IJwBmAjHb5FqWo7Wq7Qf6R
+
+
+ D_o_k_u_m_e_n_t_0000003
+ digital
+
+
+ 000004
+
+ _RO2p692zkgdsiRQMmkQArf
+ _2vljO2Bhh6leQYePmnzqED
+ _Xl1AqwKT6EEWwAPyyMz3bp
+ _2IO73BJXIP3N5kKDjZgImM
+ _y0qDEePHlePYYVdTB4sPZ8
+ _0xPOqTgXDm6tA6V4EjuO26
+ _HpQUjI8OpqkMCU5R2CyVqD
+ _6NCo6MZM5L0fpRKTQayfoE
+ _1xQ1vIulR4tjnEBAAoGO0Z
+ _SGKzK1JTc14hjyypFvod2d
+ _Z5FZCUArnATPRrenpduVWI
+ _L1bYrroT3aKdWYXP3AIVo9
+ _IcpobVzeGK0lvwjYRfyQBa
+ _qG7sApsw35bYhrWpTXXhEz
+ _oGaZtFyiKiQqMzSeA13Kz2
+ _Qe1TWhopShwLSSSsPmNtqR
+ _EHXkr0OsjGhZpik4z3IfK7
+ _cJAogjjEq7R6RCtxEivL8L
+ _cdJNqJKOQVhxO9GFO01hWj
+ _GMSlFo0t5tdZYwarv50mCL
+ _itLKxrxYH2i5rslI7HHMxu
+ _czXg34nFEEtIeNEbBwBViM
+ _Gq45ShXWYVQB6FGL4eQ6KQ
+ _ohXDvtPkQT9gjavHMhE6s6
+ _2e1DtZvIaWGol7TdeNs7mj
+ _0c7UKGRVoy9SKjluMj6iXM
+ _slVmhdd99ZM7iR1RSHYc23
+ _FeiKFdMGoa0qQuqYOOXeJ2
+ _NyuWZO4M2xpF5mkC5C4W21
+ _vqNP5Wj14Jgo2dEGb82NN5
+ _87PWsbAucVphK2i0GvuoK1
+ _V5wdSfKnvvcHVWbvXxnM4V
+ _XCX4o1SeIkuvOHUTUK4SjK
+ _hsP0JP4t9dbhHZtSLicieI
+
+
+ D_o_k_u_m_e_n_t_0000004
+ digital
+
+
+ 000005
+
+ _MMXDGhijq4qJC2aopeBET2
+ _T64yDbMxHd4zOfiGsoFs4r
+ _KE02A0CGzT96EE5vF9Vkdv
+ _InXaEi8lKBdVMY2qsaBWIY
+ _mHtXnHF6nNaJPU9b2OsETC
+ _y9mcoxJZ6Y61TTtn3URphY
+ _YC1zWSNQ6SRiTgtFGuSogz
+ _kzWnFq4N6JWQSiPehb2GbZ
+ _XZbY1IizMF0WytFYyVm6Mh
+ _K67qrCY8ooGrAR0JKNJNqR
+ _wRRzwtYII1W5VuMvb9mTiF
+ _KS4ieDUVLMUAOTIS5cjkBu
+ _sDtU2QBmgbiypc9lkRsX73
+ _8YO0xGYe4kTm2zwkuTUhsD
+ _WkYMoMj6YoZYe5dzlEl6UH
+ _rtjTAA789ADSKGFsTDQJWX
+ _vsP0fJdtAMMtVJfkr31biT
+ _ajpXoVoMzFfgZZppkaTtiG
+ _Qoj7vhZa7eoIMhSDcyh0o3
+ _e4iXpHuX2MGTYmNMwlVzIF
+ _GNmwhWlzHTpU2c8GYVu3a8
+ _Tfg1PiU4o0BuZLjcCcCcVC
+ _ffMVulAwTv5MBnB7KPPTmA
+ _LOst4IBCydIdX0ubzo3nqT
+ _3CDgIvoEtFU4wIsSBYr09R
+ _rKTEk5Hk6gpJhe10uvvpnJ
+ _HX1YwoXuUlupV5ZRiIzyWk
+ _zaoTYXgwS2noPioDE0mY4r
+ _GuoOJHUs8Yp80qpQ2RS5Te
+ _IkpFMsCq3pe9CRVlLocbs5
+
+
+ D_o_k_u_m_e_n_t_0000005
+ digital
+
+
+ 000006
+
+ _KZ4jMOlQzsRx7CaeDFivy5
+ _IBo5JKFeEDTSNo8jeJEhi0
+ _1U5ICwsUEWM9IVn8YQKd4x
+ _fYOPbYuQQzIuvBWi65PKa4
+ _2QfWWCHlcQsKdZhqVObpMi
+ _evhPU333knVoQenmoxQp3p
+ _Dzcp26EY5q9tp8FY2qHVHd
+ _RKoI7lbfb02x0CI6tp5pet
+ _rNx0K1iEzAbZ42QtZpoNPp
+ _D47AgSXy1psDGSPvu8n3Ab
+ _VC3k7lRx4gwUYGIbsDHXmx
+ _WmutZZauwa0svTrKLojbfG
+ _xTNQNQq0LeFKFH7DTO0oqp
+ _W44KutzxgdYeJ1dnfei84t
+ _2jGV9dAtXIS6bbAwNy3y0v
+ _LesD7GLY0XU3xwQ3Qam5zt
+ _eHsdgzZhcMxKL4sWSLM3wA
+ _pSF7HwXXEuG4SFNkhsTOZE
+ _v6wfzOFe9ztQ3bRIO99KSv
+ _kp7i5MpgnUZz8Od8q8BlNk
+ _A6HU42E1oIpxNtnaaakSBX
+ _fd6f3iTPfkv0mDfCIBQOB3
+ _9QNMH8PMBe4xKaMRyCS6Om
+ _lAdUCmfzik66AI6chJSlkG
+ _PWNGMrmal4Ot5TZmqB7ZYd
+ _9NcSm0FkkfcvCoiJjsRIgV
+ _NA8YTj85w888SqLKC7GUjy
+ _5ejgwi6M1HiOLIjKHV7Yh2
+ _GLgX9BNnr8REfxjuvJjAt4
+ _MwdwiJAKh9qnKVZTDwn8z0
+ _eo6Un53FiJZcuuze12DZk0
+ _CcRVDmsk1UT6yPoNWZai5D
+ _qhXvBpLc4vvUmwxiuK60zN
+ _IQH4a19oWdTYV6lnX2W60C
+ _IFuBFA9e5pYWgyhmJ0AW4c
+ _PARCvFSaN2WKsVO3euTyWg
+ _Ia3nJ4PRMlJDsRUChOzTf8
+ _sUtsReqAfPndGMezxeCTiK
+ _fS7MPLkGHqBp7U6ND9YyKP
+ _kkerbTQ67I6R6iSKEdMRsb
+ _rvyYCI9FdSbzA0fQsKulE6
+ _n7M0sIwOJL9Yk1gJFr21fB
+ _LHMWPwCslSzpp2IjZ25RWE
+ _fuy90NMhEjOIKrl1WDNsUq
+
+
+ D_o_k_u_m_e_n_t_0000006
+ digital
+
+
+ 000007
+
+ _fqsPyR6gDpgU5Z3ArCJNeM
+ _2aOx3skcAZE17WZeZv5hZq
+ _iLaCg81G9JRb6NuWVePNpF
+ _RLcfryYHYI66uKhTMv4qHz
+ _mCdJazjFP1c6gUit9aKMjR
+ _IrRzPL6OkfOyctmo47bCxq
+ _ROfPPZvW6pvjO8TNzfKJ0M
+ _f4QB89a8ikn1fcWzWFWZez
+ _r8ClVGmpWAxabOq8JC9zL3
+ _P08C99IZ3KFEjT7wgOGs6q
+ _YLiA0pG0Eil9fLj6Mb15Ce
+ _HNNLv4PqWh94DS8CLmI7et
+ _5Y5iAb70VuQLIp4TTRnIK7
+ _WdQdTCXdlo9jZkfPQRFcWh
+
+
+ D_o_k_u_m_e_n_t_0000007
+ digital
+
+
+ 000008
+
+ _RqkBRp1fesebvsPIEiUNQd
+ _pMI2DV3PWJfRkmgpAQZOhK
+ _5nQtK3pesuPnrebALdgAJp
+ _J3EBDE0Qb4NtQzy9Bqz6EP
+
+
+ D_o_k_u_m_e_n_t_0000008
+ digital
+
+
+ 000009
+
+ _Xb7BEeQlYVD5iKjhN002VT
+ _ntrnETgjGq5ZkkqXfWhfrR
+ _HLiV6GpXlYzLYBmbQG70lR
+ _JvTp5wKJSrl0xYkbxOnrRH
+ _Ex74dZAnLGkEnn26OTvug7
+ _ZnggZ8McxV0Zte6iN4FiiJ
+ _kJB5OvwTiRtaQadD87Cr4I
+ _8id5yJvFYTJt562PuQs8F7
+ _yBqDEnTHEKd4OTnTwpWs3r
+ _jMklSwpXym77rS5f7wQSl6
+
+
+ D_o_k_u_m_e_n_t_0000009
+ digital
+
+
+ 000010
+
+ _kgiVYxgtd2scGDhIt8dozW
+ _MNJhXJMd6aGxXtT4KcVAwl
+ _mOEXfGMbComnFCEn7rY4JJ
+ _OTrhzDR1bOkVBnSODpJ8vm
+ _hH1cCBvux8nppZtw8P6Y5x
+ _ByqxIi7KrjbH9cg4VAJ0LV
+ _SFCHCNPWcdGmGg9xb4V35v
+ _Fq8w7T1SOXj62CObcXUrUG
+ _RGt4S8kcTAjnftlLOtdTed
+ _8JpG2bZ4uHfJvQ8evFpzFm
+ _u8wbaevKqvjDGGIL099UIR
+ _30uCRDgDRfx6unYVsoOtTq
+ _tNXTA6AU8a9C3gFZlLi4ue
+ _znw6633dR5JIvtBpREINzq
+ _9ea8XQ157z3wSdAOQofL6j
+ _U6OWSfan1QaUoFsHgIHt8T
+ _1PMnI74tQGziV2Ac7HPxDA
+ _mbXxIjD4Wf04zsrwAXjMGY
+
+
+ D_o_k_u_m_e_n_t_0000010
+ digital
+
+
+ 000011
+
+ _TiPs089ulN6kLu00MwFiA5
+ _9yiUkB1lIPSWhjMhQBpenn
+ _z1661TWaUL5ZslBqg3lezx
+ _kTO13Tip4ClGBOIsVXaY4Z
+ _lYT860phXPJJP12SlrhW7W
+ _O6tiqxLU7KapYy8VUL1NfS
+
+
+ D_o_k_u_m_e_n_t_0000011
+ digital
+
+
+ 000012
+
+ _dxHJAQRH9faWPAy2SHGHkK
+ _iMua9Kcu3EXTkTanStTkQX
+ _OS7ocJFpaR9PHVMbEnrCRQ
+ _jqImgnt9qWQXKsFlIejtPj
+ _ZZcGoxi2beNyGA9lqipEOS
+ _P6xU6DgTXZob9HZDmU0XJc
+ _oDA7Qk2f8wL1UmS6hw6BSG
+ _IC6iMb5d5KanurFGtWQxyD
+ _qVDOwCxuC9i82QgRMcIrQu
+ _U8NnQkpVMQcNQTtLyNc39p
+
+
+ D_o_k_u_m_e_n_t_0000012
+ digital
+
+
+ 000013
+
+ _YmgmI3c08DnHMLZNhjyq25
+ _wtR8U6MzOz3thBU4s1CIY6
+ _3HCURIx5sYfdsSXiNetOUF
+ _grqjylqzmA9ZdcVAEaZ2SY
+ _e9QUoUwvAAYNAIOcHCdVgn
+ _jWHcN1SqXQhkZAEyFpVB12
+ _ZAxrrwnLQmyGnDFMUCoH34
+ _FikviVe8pvRieFmC57WlRY
+ _9HvDTqJLRAr9e2PYyVIbJT
+ _q5yN8ixVJ1Q82sfASKFrm2
+
+
+ D_o_k_u_m_e_n_t_0000013
+ digital
+
+
+ 000014
+
+ _zNm1O32k4ujOrXNyxlTreS
+ _ll3DM2BEM2B10PAziKaSI9
+ _ls1Nypyn4vcteoDjeAVbJN
+ _BGXS79BxBVD1odwUpTv6E6
+ _7nd9FIuBDLgsFmF8qBLl6Y
+ _zg9JZsUIBwXwG0oFw2oGCq
+ _KHnOoHbnUMh4C5Szg2vyq5
+ _t1A0k0NWhCCbtxiOXswMvs
+ _KEwotJieFXv7TspFOikWKR
+ _7EW6bwHe7cCrJAa5FAYnHi
+ _7c5F8YYaasRTPsu0AOXx0d
+ _KsYsTXZngBrdJJQ3JqbrE8
+ _zC6lpqdRzNQl1BFBPEFy0T
+ _Re80mq9Psk4otRUJAKjrW2
+ _uPShzQ4XHzKvyWYg1Vx12a
+ _q0OhAMl1owqvBvyyYpc3et
+ _fW7pGM0x5ZtHZd193VRY3x
+ _aH1mY7zyKnVmZRTKjLUWHK
+ _LT0ISE1KSSy55RuCFyLuGA
+ _V3glwnlSGywy82iCLZ3N5V
+ _5e7CJ88AMGziywDw1fAjWw
+ _yvp8lVYoYh31gAPkGY1wna
+ _iNVi3HL8osRWfGxljVSZIQ
+ _zeuQIbgcJIAyj7UX3UpeX5
+ _1DTjvhyqIvklV7VFymJKKh
+ _hcEywtSuawS0ZjP2lFTEdF
+ _xtR2SqdyivU2JgFlDanRYx
+ _mBtxLpyAe7WDz60HifW8D5
+ _6BKYFJBuvvQ0Dl77pvLZLS
+ _xyEdrQpxM61BeN6ZmLVq2R
+ _pg9NZbdLMGeLGkFoMO5ASq
+ _KsRi9Bzx6Ro9cjJ3yNSyWK
+
+
+ D_o_k_u_m_e_n_t_0000014
+ digital
+
+
+ 000015
+
+ _BblSEzq4DYiBdsNmhCHVgC
+ _9YFtc0bslkVLZInZvnVrR2
+ _aVV54EggtVulKdoLPzFL8U
+ _1FF9xChDJCKjSPDIM84oUE
+ _ohyOthTAk4aooIrojg0YKQ
+ _6c3OTNj6vrh2prG5A87JRL
+ _IwwCtk50jMU9H5N909OTYq
+ _BLlOwNRwRVYxIGMo7905q5
+ _Ka9zQVJNk9ETDITX2r9kS6
+ _svnHuG5fj6LKMvOBJPIWeE
+
+
+ D_o_k_u_m_e_n_t_0000015
+ digital
+
+
+ 000016
+
+ _qvO2zsx328rTNX4bdzB06o
+ _dYtCZukGcGw5Dv9rpH7Phf
+ _qL6TWVbmxizhVqd7JTMlJr
+ _gnY2RtL225dXOzn34EsN0s
+
+
+ D_o_k_u_m_e_n_t_0000016
+ digital
+
+
+ 000017
+
+ _FqoZqKtYsQn9iAdoqqv1cI
+ _riEcze9FkwXNAgtur3vhvB
+ _wrbiTSyMyT93k4b9yhnd8A
+ _QC7MZ9myhW7QgxL7ELdiQV
+ _EltAAZKE7xX72Nr4kNUT7f
+ _oSKAG9iswtYdLdEoZOgNZI
+ _MPUtT4LAN6k1X9i205JK4v
+ _JnLmA6SzL8PXhLuSAjD6BN
+ _RfwXpYysjDoYf1KN9ZDc9K
+ _t86rSQb97ckC4ZprJoDUqP
+ _aZTvmXomyNbDu78bf18jPb
+ _lCNbsKsl9D7BObhJtz81Sw
+ _ao6Adl1bXk9YAFXqcOgECY
+ _o8pOoPrSOEdgE8CMLlbOFq
+ _FDHQdkVRY6R3kiMBSVAkuj
+ _l3La0Qs6HdEVsmPEtnefcJ
+
+
+ D_o_k_u_m_e_n_t_0000017
+ digital
+
+
+ 000018
+
+ _mknnbMIDwFwyyAhb0nNNAi
+ _bVWoiFVEofzRW0cjYiwZiU
+ _a3UQBD05UK5O75fbdz66oY
+ _MxAgCiLVHDdzLmFTqqJgvm
+ _c7FINosFeQtOUoVT1hHhTO
+ _jxDTghxxNxUFP0nh4DmCSF
+ _ehXSmIcDPXHcBRZRcEz93t
+ _QX9ItkC2VPpvB8rdhoLTXL
+
+ _fZzi3dX2jvrwakvY6jeJS8
+
+
+
+
+
+
+
+
+ Eingangsprüfung automatisiert
+ Automated tests run
+
+ XML well formed and valid:
+ passed
+Structural Integrity:
+ passed
+File Names Correct:
+ passed
+SIP content structure plausible:
+ passed
+Virus Check:
+ passed
+File Formats:
+ passed
+
+ Comment:
+
+
+ 2023-08-31T15:36:11.239+02:00
+ 2023-08-31T15:36:23.236+02:00
+
+ Andreas Christe
+
+
+ Eingangsprüfung manuell
+ SIP Approved for Ingest
+
+ 2023-08-31T15:36:23.236+02:00
+ 2023-08-31T15:36:23.236+02:00
+
+ Andreas Christe
+
+