Initial commit

This commit is contained in:
2025-10-26 16:22:50 +01:00
commit 4d6c354436
12 changed files with 1193 additions and 0 deletions

58
go.mod Normal file
View File

@@ -0,0 +1,58 @@
module varia-go
go 1.25.2
require (
github.com/roemer/goext v0.8.0
github.com/roemer/gotaskr v0.7.0
)
require (
dario.cat/mergo v1.0.1 // indirect
github.com/CycloneDX/cyclonedx-go v0.9.2 // indirect
github.com/Microsoft/go-winio v0.6.2 // indirect
github.com/ProtonMail/go-crypto v1.1.6 // indirect
github.com/andybalholm/brotli v1.1.1 // indirect
github.com/cloudflare/circl v1.6.1 // indirect
github.com/cyphar/filepath-securejoin v0.4.1 // indirect
github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5 // indirect
github.com/emirpasic/gods v1.18.1 // indirect
github.com/fatih/color v1.18.0 // indirect
github.com/forPelevin/gomoji v1.3.0 // indirect
github.com/go-git/gcfg v1.5.1-0.20230307220236-3a3c6141e376 // indirect
github.com/go-git/go-billy/v5 v5.6.2 // indirect
github.com/go-git/go-git/v5 v5.14.0 // indirect
github.com/golang-jwt/jwt/v4 v4.5.2 // indirect
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 // indirect
github.com/golang/snappy v0.0.4 // indirect
github.com/gookit/color v1.5.4 // indirect
github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99 // indirect
github.com/jfrog/archiver/v3 v3.6.1 // indirect
github.com/jfrog/build-info-go v1.10.17 // indirect
github.com/jfrog/gofrog v1.7.6 // indirect
github.com/jfrog/jfrog-client-go v1.54.7 // indirect
github.com/kevinburke/ssh_config v1.2.0 // indirect
github.com/klauspost/compress v1.17.11 // indirect
github.com/klauspost/cpuid/v2 v2.2.9 // indirect
github.com/klauspost/pgzip v1.2.6 // indirect
github.com/mattn/go-colorable v0.1.13 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/minio/sha256-simd v1.0.1 // indirect
github.com/nwaples/rardecode v1.1.3 // indirect
github.com/pierrec/lz4/v4 v4.1.22 // indirect
github.com/pjbgf/sha1cd v0.3.2 // indirect
github.com/rivo/uniseg v0.4.7 // indirect
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3 // indirect
github.com/skeema/knownhosts v1.3.1 // indirect
github.com/ulikunitz/xz v0.5.12 // indirect
github.com/xanzy/ssh-agent v0.3.3 // indirect
github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8 // indirect
github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e // indirect
golang.org/x/crypto v0.36.0 // indirect
golang.org/x/exp v0.0.0-20250305212735-054e65f0b394 // indirect
golang.org/x/net v0.38.0 // indirect
golang.org/x/sync v0.12.0 // indirect
golang.org/x/sys v0.31.0 // indirect
golang.org/x/term v0.30.0 // indirect
gopkg.in/warnings.v0 v0.1.2 // indirect
)

177
go.sum Normal file
View File

@@ -0,0 +1,177 @@
dario.cat/mergo v1.0.1 h1:Ra4+bf83h2ztPIQYNP99R6m+Y7KfnARDfID+a+vLl4s=
dario.cat/mergo v1.0.1/go.mod h1:uNxQE+84aUszobStD9th8a29P2fMDhsBdgRYvZOxGmk=
github.com/CycloneDX/cyclonedx-go v0.9.2 h1:688QHn2X/5nRezKe2ueIVCt+NRqf7fl3AVQk+vaFcIo=
github.com/CycloneDX/cyclonedx-go v0.9.2/go.mod h1:vcK6pKgO1WanCdd61qx4bFnSsDJQ6SbM2ZuMIgq86Jg=
github.com/Microsoft/go-winio v0.5.2/go.mod h1:WpS1mjBmmwHBEWmogvA2mj8546UReBk4v8QkMxJ6pZY=
github.com/Microsoft/go-winio v0.6.2 h1:F2VQgta7ecxGYO8k3ZZz3RS8fVIXVxONVUPlNERoyfY=
github.com/Microsoft/go-winio v0.6.2/go.mod h1:yd8OoFMLzJbo9gZq8j5qaps8bJ9aShtEA8Ipt1oGCvU=
github.com/ProtonMail/go-crypto v1.1.6 h1:ZcV+Ropw6Qn0AX9brlQLAUXfqLBc7Bl+f/DmNxpLfdw=
github.com/ProtonMail/go-crypto v1.1.6/go.mod h1:rA3QumHc/FZ8pAHreoekgiAbzpNsfQAosU5td4SnOrE=
github.com/andybalholm/brotli v1.1.1 h1:PR2pgnyFznKEugtsUo0xLdDop5SKXd5Qf5ysW+7XdTA=
github.com/andybalholm/brotli v1.1.1/go.mod h1:05ib4cKhjx3OQYUY22hTVd34Bc8upXjOLL2rKwwZBoA=
github.com/anmitsu/go-shlex v0.0.0-20200514113438-38f4b401e2be h1:9AeTilPcZAjCFIImctFaOjnTIavg87rW78vTPkQqLI8=
github.com/anmitsu/go-shlex v0.0.0-20200514113438-38f4b401e2be/go.mod h1:ySMOLuWl6zY27l47sB3qLNK6tF2fkHG55UZxx8oIVo4=
github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5 h1:0CwZNZbxp69SHPdPJAN/hZIm0C4OItdklCFmMRWYpio=
github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs=
github.com/bradleyjkemp/cupaloy/v2 v2.8.0 h1:any4BmKE+jGIaMpnU8YgH/I2LPiLBufr6oMMlVBbn9M=
github.com/bradleyjkemp/cupaloy/v2 v2.8.0/go.mod h1:bm7JXdkRd4BHJk9HpwqAI8BoAY1lps46Enkdqw6aRX0=
github.com/cloudflare/circl v1.6.1 h1:zqIqSPIndyBh1bjLVVDHMPpVKqp8Su/V+6MeDzzQBQ0=
github.com/cloudflare/circl v1.6.1/go.mod h1:uddAzsPgqdMAYatqJ0lsjX1oECcQLIlRpzZh3pJrofs=
github.com/cyphar/filepath-securejoin v0.4.1 h1:JyxxyPEaktOD+GAnqIqTf9A8tHyAG22rowi7HkoSU1s=
github.com/cyphar/filepath-securejoin v0.4.1/go.mod h1:Sdj7gXlvMcPZsbhwhQ33GguGLDGQL7h7bg04C/+u9jI=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5 h1:iFaUwBSo5Svw6L7HYpRu/0lE3e0BaElwnNO1qkNQxBY=
github.com/dsnet/compress v0.0.2-0.20210315054119-f66993602bf5/go.mod h1:qssHWj60/X5sZFNxpG4HBPDHVqxNm4DfnCKgrbZOT+s=
github.com/dsnet/golib v0.0.0-20171103203638-1ea166775780/go.mod h1:Lj+Z9rebOhdfkVLjJ8T6VcRQv3SXugXy999NBtR9aFY=
github.com/elazarl/goproxy v1.7.2 h1:Y2o6urb7Eule09PjlhQRGNsqRfPmYI3KKQLFpCAV3+o=
github.com/elazarl/goproxy v1.7.2/go.mod h1:82vkLNir0ALaW14Rc399OTTjyNREgmdL2cVoIbS6XaE=
github.com/emirpasic/gods v1.18.1 h1:FXtiHYKDGKCW2KzwZKx0iC0PQmdlorYgdFG9jPXJ1Bc=
github.com/emirpasic/gods v1.18.1/go.mod h1:8tpGGwCnJ5H4r6BWwaV6OrWmMoPhUl5jm/FMNAnJvWQ=
github.com/fatih/color v1.18.0 h1:S8gINlzdQ840/4pfAwic/ZE0djQEH3wM94VfqLTZcOM=
github.com/fatih/color v1.18.0/go.mod h1:4FelSpRwEGDpQ12mAdzqdOukCy4u8WUtOY6lkT/6HfU=
github.com/forPelevin/gomoji v1.3.0 h1:WPIOLWB1bvRYlKZnSSEevLt3IfKlLs+tK+YA9fFYlkE=
github.com/forPelevin/gomoji v1.3.0/go.mod h1:mM6GtmCgpoQP2usDArc6GjbXrti5+FffolyQfGgPboQ=
github.com/gliderlabs/ssh v0.3.8 h1:a4YXD1V7xMF9g5nTkdfnja3Sxy1PVDCj1Zg4Wb8vY6c=
github.com/gliderlabs/ssh v0.3.8/go.mod h1:xYoytBv1sV0aL3CavoDuJIQNURXkkfPA/wxQ1pL1fAU=
github.com/go-git/gcfg v1.5.1-0.20230307220236-3a3c6141e376 h1:+zs/tPmkDkHx3U66DAb0lQFJrpS6731Oaa12ikc+DiI=
github.com/go-git/gcfg v1.5.1-0.20230307220236-3a3c6141e376/go.mod h1:an3vInlBmSxCcxctByoQdvwPiA7DTK7jaaFDBTtu0ic=
github.com/go-git/go-billy/v5 v5.6.2 h1:6Q86EsPXMa7c3YZ3aLAQsMA0VlWmy43r6FHqa/UNbRM=
github.com/go-git/go-billy/v5 v5.6.2/go.mod h1:rcFC2rAsp/erv7CMz9GczHcuD0D32fWzH+MJAU+jaUU=
github.com/go-git/go-git-fixtures/v4 v4.3.2-0.20231010084843-55a94097c399 h1:eMje31YglSBqCdIqdhKBW8lokaMrL3uTkpGYlE2OOT4=
github.com/go-git/go-git-fixtures/v4 v4.3.2-0.20231010084843-55a94097c399/go.mod h1:1OCfN199q1Jm3HZlxleg+Dw/mwps2Wbk9frAWm+4FII=
github.com/go-git/go-git/v5 v5.14.0 h1:/MD3lCrGjCen5WfEAzKg00MJJffKhC8gzS80ycmCi60=
github.com/go-git/go-git/v5 v5.14.0/go.mod h1:Z5Xhoia5PcWA3NF8vRLURn9E5FRhSl7dGj9ItW3Wk5k=
github.com/golang-jwt/jwt/v4 v4.5.2 h1:YtQM7lnr8iZ+j5q71MGKkNw9Mn7AjHM68uc9g5fXeUI=
github.com/golang-jwt/jwt/v4 v4.5.2/go.mod h1:m21LjoU+eqJr34lmDMbreY2eSTRJ1cv77w39/MY0Ch0=
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 h1:f+oWsMOmNPc8JmEHVZIycC7hBoQxHH9pNKQORJNozsQ=
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8/go.mod h1:wcDNUvekVysuuOpQKo3191zZyTpiI6se1N1ULghS0sw=
github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM=
github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8=
github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU=
github.com/gookit/color v1.5.4 h1:FZmqs7XOyGgCAxmWyPslpiok1k05wmY3SJTytgvYFs0=
github.com/gookit/color v1.5.4/go.mod h1:pZJOeOS8DM43rXbp4AZo1n9zCU2qjpcRko0b6/QJi9w=
github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99 h1:BQSFePA1RWJOlocH6Fxy8MmwDt+yVQYULKfN0RoTN8A=
github.com/jbenet/go-context v0.0.0-20150711004518-d14ea06fba99/go.mod h1:1lJo3i6rXxKeerYnT8Nvf0QmHCRC1n8sfWVwXF2Frvo=
github.com/jfrog/archiver/v3 v3.6.1 h1:LOxnkw9pOn45DzCbZNFV6K0+6dCsQ0L8mR3ZcujO5eI=
github.com/jfrog/archiver/v3 v3.6.1/go.mod h1:VgR+3WZS4N+i9FaDwLZbq+jeU4B4zctXL+gL4EMzfLw=
github.com/jfrog/build-info-go v1.10.17 h1:wnVd9KkyFGQgNL+oU1wXyJB7/Ui9O/MqUnNKUMsyoRw=
github.com/jfrog/build-info-go v1.10.17/go.mod h1:szdz9+WzB7+7PGnILLUgyY+OF5qD5geBT7UGNIxibyw=
github.com/jfrog/gofrog v1.7.6 h1:QmfAiRzVyaI7JYGsB7cxfAJePAZTzFz0gRWZSE27c6s=
github.com/jfrog/gofrog v1.7.6/go.mod h1:ntr1txqNOZtHplmaNd7rS4f8jpA5Apx8em70oYEe7+4=
github.com/jfrog/jfrog-client-go v1.54.7 h1:S1geo9T5ZCAb7EkXSv+NJ0K8+yhDsxlrybHTosCilIg=
github.com/jfrog/jfrog-client-go v1.54.7/go.mod h1:cOy7Pn34bGtjp0eWHADTRJG5Er0qVnJIz04u+NGEpcQ=
github.com/kevinburke/ssh_config v1.2.0 h1:x584FjTGwHzMwvHx18PXxbBVzfnxogHaAReU4gf13a4=
github.com/kevinburke/ssh_config v1.2.0/go.mod h1:CT57kijsi8u/K/BOFA39wgDQJ9CxiF4nAY/ojJ6r6mM=
github.com/klauspost/compress v1.4.1/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A=
github.com/klauspost/compress v1.17.11 h1:In6xLpyWOi1+C7tXUUWv2ot1QvBjxevKAaI6IXrJmUc=
github.com/klauspost/compress v1.17.11/go.mod h1:pMDklpSncoRMuLFrf1W9Ss9KT+0rH90U12bZKk7uwG0=
github.com/klauspost/cpuid v1.2.0/go.mod h1:Pj4uuM528wm8OyEC2QMXAi2YiTZ96dNQPGgoMS4s3ek=
github.com/klauspost/cpuid/v2 v2.2.9 h1:66ze0taIn2H33fBvCkXuv9BmCwDfafmiIVpKV9kKGuY=
github.com/klauspost/cpuid/v2 v2.2.9/go.mod h1:rqkxqrZ1EhYM9G+hXH7YdowN5R5RGN6NK4QwQ3WMXF8=
github.com/klauspost/pgzip v1.2.6 h1:8RXeL5crjEUFnR2/Sn6GJNWtSQ3Dk8pq4CL3jvdDyjU=
github.com/klauspost/pgzip v1.2.6/go.mod h1:Ch1tH69qFZu15pkjo5kYi6mth2Zzwzt50oCQKQE9RUs=
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE=
github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk=
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA=
github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg=
github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
github.com/minio/sha256-simd v1.0.1 h1:6kaan5IFmwTNynnKKpDHe6FWHohJOHhCPchzK49dzMM=
github.com/minio/sha256-simd v1.0.1/go.mod h1:Pz6AKMiUdngCLpeTL/RJY1M9rUuPMYujV5xJjtbRSN8=
github.com/nwaples/rardecode v1.1.3 h1:cWCaZwfM5H7nAD6PyEdcVnczzV8i/JtotnyW/dD9lEc=
github.com/nwaples/rardecode v1.1.3/go.mod h1:5DzqNKiOdpKKBH87u8VlvAnPZMXcGRhxWkRpHbbfGS0=
github.com/onsi/gomega v1.34.1 h1:EUMJIKUjM8sKjYbtxQI9A4z2o+rruxnzNvpknOXie6k=
github.com/onsi/gomega v1.34.1/go.mod h1:kU1QgUvBDLXBJq618Xvm2LUX6rSAfRaFRTcdOeDLwwY=
github.com/pierrec/lz4/v4 v4.1.22 h1:cKFw6uJDK+/gfw5BcDL0JL5aBsAFdsIT18eRtLj7VIU=
github.com/pierrec/lz4/v4 v4.1.22/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4=
github.com/pjbgf/sha1cd v0.3.2 h1:a9wb0bp1oC2TGwStyn0Umc/IGKQnEgF0vVaZ8QF8eo4=
github.com/pjbgf/sha1cd v0.3.2/go.mod h1:zQWigSxVmsHEZow5qaLtPYxpcKMMQpa09ixqBxuCS6A=
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/rivo/uniseg v0.4.7 h1:WUdvkW8uEhrYfLC4ZzdpI2ztxP1I582+49Oc5Mq64VQ=
github.com/rivo/uniseg v0.4.7/go.mod h1:FN3SvrM+Zdj16jyLfmOkMNblXMcoc8DfTHruCPUcx88=
github.com/roemer/goext v0.8.0 h1:gdx2gjDAq1nshbvFSrqR/wA2CzLLJlJEgc/DfdYhQTQ=
github.com/roemer/goext v0.8.0/go.mod h1:D+HvjseqdlevkQ9QeCME6XvXoUfJwmlyRrY3YfmTnB8=
github.com/roemer/gotaskr v0.7.0 h1:zP2SOVJAV4yGdItmEIYjYxgXF8gzmX+y8a6tnbXOz0o=
github.com/roemer/gotaskr v0.7.0/go.mod h1:ue5tvkLn9BG8i41JogicOxS5rYqJlbHW8Hst9VXxliA=
github.com/rogpeppe/go-internal v1.14.1 h1:UQB4HGPB6osV0SQTLymcB4TgvyWu6ZyliaW0tI/otEQ=
github.com/rogpeppe/go-internal v1.14.1/go.mod h1:MaRKkUm5W0goXpeCfT7UZI6fk/L7L7so1lCWt35ZSgc=
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3 h1:n661drycOFuPLCN3Uc8sB6B/s6Z4t2xvBgU1htSHuq8=
github.com/sergi/go-diff v1.3.2-0.20230802210424-5b0b94c5c0d3/go.mod h1:A0bzQcvG0E7Rwjx0REVgAGH58e96+X0MeOfepqsbeW4=
github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0=
github.com/skeema/knownhosts v1.3.1 h1:X2osQ+RAjK76shCbvhHHHVl3ZlgDm8apHEHFqRjnBY8=
github.com/skeema/knownhosts v1.3.1/go.mod h1:r7KTdC8l4uxWRyK2TpQZ/1o5HaSzh06ePQNxPwTcfiY=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U=
github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U=
github.com/terminalstatic/go-xsd-validate v0.1.6 h1:TenYeQ3eY631qNi1/cTmLH/s2slHPRKTTHT+XSHkepo=
github.com/terminalstatic/go-xsd-validate v0.1.6/go.mod h1:18lsvYFofBflqCrvo1umpABZ99+GneNTw2kEEc8UPJw=
github.com/ulikunitz/xz v0.5.8/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14=
github.com/ulikunitz/xz v0.5.12 h1:37Nm15o69RwBkXM0J6A5OlE67RZTfzUxTj8fB3dfcsc=
github.com/ulikunitz/xz v0.5.12/go.mod h1:nbz6k7qbPmH4IRqmfOplQw/tblSgqTqBwxkY0oWt/14=
github.com/xanzy/ssh-agent v0.3.3 h1:+/15pJfg/RsTxqYcX6fHqOXZwwMP+2VyYWJeWM2qQFM=
github.com/xanzy/ssh-agent v0.3.3/go.mod h1:6dzNDKs0J9rVPHPhaGCukekBHKqfl+L3KghI1Bc68Uw=
github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f h1:J9EGpcZtP0E/raorCMxlFGSTBrsSlaDGf3jU/qvAE2c=
github.com/xeipuuv/gojsonpointer v0.0.0-20180127040702-4e3ac2762d5f/go.mod h1:N2zxlSyiKSe5eX1tZViRH5QA0qijqEDrYZiPEAiq3wU=
github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 h1:EzJWgHovont7NscjpAxXsDA8S8BMYve8Y5+7cuRE7R0=
github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415/go.mod h1:GwrjFmJcFw6At/Gs6z4yjiIwzuJ1/+UwLxMQDVQXShQ=
github.com/xeipuuv/gojsonschema v1.2.0 h1:LhYJRs+L4fBtjZUfuSZIKGeVu0QRy8e5Xi7D17UxZ74=
github.com/xeipuuv/gojsonschema v1.2.0/go.mod h1:anYRn/JVcOK2ZgGU+IjEV4nwlhoK5sQluxsYJ78Id3Y=
github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8 h1:nIPpBwaJSVYIxUFsDv3M8ofmx9yWTog9BfvIu0q41lo=
github.com/xi2/xz v0.0.0-20171230120015-48954b6210f8/go.mod h1:HUYIGzjTL3rfEspMxjDjgmT5uz5wzYJKVo23qUhYTos=
github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e h1:JVG44RsyaB9T2KIHavMF/ppJZNG9ZpyihvCd0w101no=
github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e/go.mod h1:RbqR21r5mrJuqunuUZ/Dhy/avygyECGrLceyNeo4LiM=
github.com/xyproto/randomstring v1.0.5 h1:YtlWPoRdgMu3NZtP45drfy1GKoojuR7hmRcnhZqKjWU=
github.com/xyproto/randomstring v1.0.5/go.mod h1:rgmS5DeNXLivK7YprL0pY+lTuhNQW3iGxZ18UQApw/E=
golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
golang.org/x/crypto v0.36.0 h1:AnAEvhDddvBdpY+uR+MyHmuZzzNqXSe/GvuDeob5L34=
golang.org/x/crypto v0.36.0/go.mod h1:Y4J0ReaxCR1IMaabaSMugxJES1EpwhBHhv2bDHklZvc=
golang.org/x/exp v0.0.0-20250305212735-054e65f0b394 h1:nDVHiLt8aIbd/VzvPWN6kSOPE7+F/fNFDSXLVYkE/Iw=
golang.org/x/exp v0.0.0-20250305212735-054e65f0b394/go.mod h1:sIifuuw/Yco/y6yb6+bDNfyeQ/MdPUy/hKEMYQV17cM=
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
golang.org/x/net v0.38.0 h1:vRMAPTMaeGqVhG5QyLJHqNDwecKTomGeqbnfZyKlBI8=
golang.org/x/net v0.38.0/go.mod h1:ivrbrMbzFq5J41QOQh0siUuly180yBYtLp+CKbEaFx8=
golang.org/x/sync v0.12.0 h1:MHc5BpPuC30uJk597Ri8TV3CNZcTLu6B6z4lJy+g6Jw=
golang.org/x/sync v0.12.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.31.0 h1:ioabZlmFYtWhL+TRYpcnNlLwhyxaM9kWTDEmfnprqik=
golang.org/x/sys v0.31.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/term v0.30.0 h1:PQ39fJZ+mfadBm0y5WlL4vlM7Sx1Hgf13sMIY2+QS9Y=
golang.org/x/term v0.30.0/go.mod h1:NYYFdzHoI5wRh/h5tDMdMqCqPJZEuNqVR5xJLd/n67g=
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY=
golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
gopkg.in/warnings.v0 v0.1.2 h1:wFXVbFY8DY5/xOe1ECiWdKCzZlxgshcYVNkBHstARME=
gopkg.in/warnings.v0 v0.1.2/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

32
main.go Normal file
View File

@@ -0,0 +1,32 @@
package main
import (
"fmt"
"os"
"varia-go/tasks"
"github.com/roemer/gotaskr"
)
func main() {
os.Exit(gotaskr.Execute())
}
func init() {
gotaskr.Task("Epic-Links", func() error {
return (&tasks.EpicLinkTask{}).Run()
})
gotaskr.Task("Create-Mega-Account", func() error {
return (&tasks.MegaAccountTask{}).Run()
})
// args: --folder=\\nas03\Dump
gotaskr.Task("Black-Border-Analyze", func() error {
folder, hasArg := gotaskr.GetArgument("folder")
if !hasArg {
return fmt.Errorf("folder argument is required")
}
return tasks.NewBlackBorderAnalyzeTask("blackborder.log").Run(folder)
})
}

28
main_releases.go Normal file
View File

@@ -0,0 +1,28 @@
package main
import (
"time"
"varia-go/task_pack_release"
"github.com/roemer/gotaskr"
)
func init() {
gotaskr.Task("Jimmy-Neutron-Extra", func() error {
return task_pack_release.PackRelease(
`\\nas03\storage\_Incoming\_Reencode\The Adventures of Jimmy Neutron\_enc\Extras\Jimmy Neutron - S01E00 - Pilotfolge - Runaway Rocketboy.mkv`,
`F:\jim\extra_2`, "jim-extra", "serienfans.org", "500m",
&task_pack_release.NfoCreatorSettings{
Title: task_pack_release.NewTitleBuilder("Jimmy.Neutron.S01E00.Pilot.Runaway.Rocketboy").DVDRip().X264().Build(),
Infos: []*task_pack_release.KeyValue{
{"Release Date", time.Now().Format(time.DateOnly)},
{"Source", task_pack_release.Dvd},
{"Subs", "German"},
{"Video", "768x576"},
{"Audio 1", "English"},
},
Notes: "Degrained, sharpened, cropped.",
},
)
})
}

View File

@@ -0,0 +1,108 @@
package task_pack_release
import (
"fmt"
"os"
"os/exec"
"path/filepath"
"regexp"
"strings"
)
var rarPath = `C:\Program Files\WinRAR\WinRAR.exe`
func compress(srcPath string, dstPath string, releaseName string, archivePwd string, archiveSize string, nfoFilePath string) error {
// Check if the content is a directory or a single file
fi, err := os.Stat(srcPath)
if err != nil {
return fmt.Errorf("failed to stat content path: %w", err)
}
// Collect the files to be archived
var files []string
if fi.IsDir() {
dirEntries, err := os.ReadDir(srcPath)
if err != nil {
return fmt.Errorf("failed to read directory: %w", err)
}
for _, entry := range dirEntries {
if entry.IsDir() {
continue
}
filePath := filepath.Join(srcPath, entry.Name())
if filepath.Ext(filePath) != ".nfo" {
files = append(files, filePath)
}
}
} else {
files = append(files, srcPath)
}
os.MkdirAll(dstPath, os.ModePerm)
// Process the files
for _, entry := range files {
fileName := filepath.Base(entry)
fixedFileName := getFixedName(fileName)
fixedFilePath := filepath.Join(dstPath, fixedFileName)
if err := copyFile(entry, fixedFilePath); err != nil {
return err
}
archiveName := buildArchiveName(fileName, releaseName)
archivePath := filepath.Join(dstPath, archiveName)
args := []string{
"a", "-ma4", "-m0", "-ep",
"-v" + archiveSize,
"-rr3p",
"-hp" + archivePwd,
archivePath,
fixedFilePath,
}
if nfoFilePath != "" {
args = append(args, nfoFilePath)
}
cmd := exec.Command(rarPath, args...)
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
fmt.Printf("Creating archive: %s\n", archiveName)
err = cmd.Run()
if err != nil {
return fmt.Errorf("winrar failed: %w", err)
}
os.Remove(fixedFilePath)
}
return nil
}
func getFixedName(name string) string {
replacer := strings.NewReplacer(
"ä", "ae",
"ö", "oe",
"ü", "ue",
//" ", ".",
)
return replacer.Replace(name)
}
func buildArchiveName(fileName string, releaseName string) string {
re := regexp.MustCompile(`(?i)^(.*?)[\-\.\s]*(?:s?(\d+))?([ex])(\d+)([a-f]?)[\-\.\s]*(.*)$`)
m := re.FindStringSubmatch(fileName)
if len(m) == 0 {
return fmt.Sprintf("%s.rar", releaseName)
}
season := m[2]
epd := m[3]
ep := m[4]
suff := m[5]
if season != "" {
return fmt.Sprintf("%s.S%s%s%s.rar", releaseName, season, epd, ep)
}
return fmt.Sprintf("%s.%s%s%s.rar", releaseName, epd, ep, suff)
}

View File

@@ -0,0 +1,50 @@
/Maaa*p
>Oh$oci>>{8&*m[.
""JWv!i>>xci>>{ki>>!1#k>.
'1@ti>>>>>>xci>>{ki>>>>>i[*0`
.]B~>>>>>>>>>xci>>{ki>>>>>>>>i*x`
.^hvi>>>>>iii!>uz?]_)k!ii>>>>>>>>[W!.
':B?>>+t&%Whu1~l!iiii!!+)coW%*x_>i>!*}.
.:&wWZf+~nmo%pUur(}{}})jnUZ%MpC)<1YBbxo1'
!BL<_L%o|!i>>>>>>>>>>>>>>>>>>>>iiixMBQ--pBi
;$8c_i>>>i!+fLqh&$*bppd*$8apOn[ii>>>>i</b%Z
^$i>>>($%b{!i>>>>>>>>>>>>>>>>i!<u8B*{>i>ixn'
';BL8L}iiiii~?{(tncYJCCCYcnf(1]+>!iiii[UWqCw`
`i$&@BBWBn|B$$$$%r&jjjjjjjOJW$$$$$YYB%BB@8#u,
:$Mz)}]?{B!:d$$d:uM+++++_-Yb'z$$#]:bX?[[)v8W,.
`)O~$+i!!!!?WBoWBk(M+++++++Ycc%@k@%u!!!!i~m(rQ""
.:@!iZX>!!!!!!!!!!!/M+++++++Yc!!!!!!!!!!!>rpi+B;
.>%i>ih|>!!!!!!!!!!1$_++++++$}!!!!!!!!!!>?$i>i8+`
'}8>>>>#(>!!!!!!!!!+)@L[+[X8t]!!!!!!!!!>-8->>>Uj`
'}8>>>>ibc>!!!!!!!!>>}(|r||}+>!!!!!!!!>($>>>>>Jt^
'~%i>>>>i/&]i!!!!!!!!!!iii!!!!!!!!!!i<*ui>>>>>@~^
.!w1>>>>>>ifB(>!!!!!!!!!!!!!!!!!!!>]%U>>>>>>>[%!`
.^<$+>>>>>>>>~LWJ]i!!!!!!!!!!!!]zMm-i>>>>>>>~B+,
,_%]>>>>>>>>>>i/B[>!!!!!!!!>8vi>>>>>>>>>>_@[,'
.""~Zb-ii>>>i}bor}~i!!!!!!!!>[tkh|ii>>>i~qd_;.
^I~Z$@BB$kJfW%ciI!!!!!!!!ItM@v|zWBB@$&(I^
-Bh|i>ibX!i_%B8t~{nCZZZ0v)+{$%@/!i>B_>i<C8r^
<M$B~>>>>>>no>><B8@8df_~~+}cW@8&@[>>-B<>>>>>>>-BM-
.chhhhkkkkkkkhaahkkkaabkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkhhhhhhhm]
.B' d
:z@oUUUZt, d+
qz!!!!!!!!j0 dWWfd+U8Y
+@imf!!!!!!!!!!{u ======================= d!!!XMld>ivp
^W[!!!mf!!!!!!!!!!{u === Roemer Presents === d!!!!!!!p(
<&!!!!!LX!!!!!!!!!!/x ======================= d!!!!!ldt
d_!!!!!ldX!!!!!!!ljv h!!!!l8i
8!!!!!!!!~bW$MMMk| k!!!]$`
Ut!!!!!!!!!>B' b!!rd
'W!!!!!!!!!>B' {{ .Title1 }} blpj
'Bf!!!!!lt&B' {{ .Title2 }} bmb.
.dM8Wa) 'B' d;{{ if .Infos }}
{{- range .Infos }}
'B' {{ . }} d{{ end }}
'B' d{{ end }}{{ if .Notes }}
'B' === Notes === d
'B' d
{{- range .Notes }}
'B' {{ . }} d{{ end }}
'B' d{{ end }}
;#nffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffo1

272
task_pack_release/nfo.go Normal file
View File

@@ -0,0 +1,272 @@
package task_pack_release
import (
"bytes"
"fmt"
"os"
"path/filepath"
"slices"
"strings"
"text/template"
)
type NfoCreatorSettings struct {
Title string
Infos []*KeyValue
Notes string
}
type KeyValue struct {
Key string
Value string
}
type nfoTemplateData struct {
Title1 string
Title2 string
Infos []string
Notes []string
}
func CreateNfo(dstPath string, settings *NfoCreatorSettings) (string, error) {
maxAllowedWidth := 65
// Prepare
nfoTemplateData := &nfoTemplateData{}
// Handle the title
title := strings.ReplaceAll(settings.Title, " ", ".")
title = strings.ReplaceAll(title, "(", "")
title = strings.ReplaceAll(title, ")", "")
title = strings.ReplaceAll(title, ",", "")
title = strings.ReplaceAll(title, "&", "")
title = strings.ReplaceAll(title, "..", ".")
nfoTemplateData.Title1 = title
nfoTemplateData.Title2 = ""
if len(title) > maxAllowedWidth {
splitIndex := strings.LastIndexAny(title[:maxAllowedWidth], ".-")
nfoTemplateData.Title1 = title[:splitIndex]
nfoTemplateData.Title2 = title[splitIndex:]
}
nfoTemplateData.Title1 = fmt.Sprintf("%-*s", maxAllowedWidth, nfoTemplateData.Title1)
nfoTemplateData.Title2 = fmt.Sprintf("%-*s", maxAllowedWidth, nfoTemplateData.Title2)
// Handle Infos
maxKey := slices.MaxFunc(settings.Infos, func(a, b *KeyValue) int {
if len(a.Key) < len(b.Key) {
return -1
} else if len(a.Key) > len(b.Key) {
return 1
}
return 0
})
maxKeyLen := len(maxKey.Key)
for _, info := range settings.Infos {
nfoTemplateData.Infos = append(nfoTemplateData.Infos, fmt.Sprintf("%-*s : %-*s", maxKeyLen, info.Key, maxAllowedWidth-maxKeyLen-3, info.Value))
}
// Handle Notes
noteLines := strings.SplitSeq(settings.Notes, "\n")
for note := range noteLines {
if len(note) > maxAllowedWidth {
splitIndex := strings.LastIndexAny(note[:maxAllowedWidth], " ")
nfoTemplateData.Notes = append(nfoTemplateData.Notes, fmt.Sprintf("%-*s", maxAllowedWidth, note[:splitIndex]))
nfoTemplateData.Notes = append(nfoTemplateData.Notes, fmt.Sprintf("%-*s", maxAllowedWidth, note[splitIndex+1:]))
} else {
nfoTemplateData.Notes = append(nfoTemplateData.Notes, fmt.Sprintf("%-*s", maxAllowedWidth, note))
}
}
// Parse the template file
t1, err := template.New("info.nfo.tmpl").ParseFiles("./task_pack_release/info.nfo.tmpl")
if err != nil {
return "", err
}
// Execute the template to a memory buffer
var buf bytes.Buffer
if err := t1.Execute(&buf, nfoTemplateData); err != nil {
return "", err
}
// Convert the buffer to string
content := buf.String()
os.MkdirAll(dstPath, os.ModePerm)
nfoFilePath := filepath.Join(dstPath, fmt.Sprintf("%s.nfo", title))
if err := os.WriteFile(nfoFilePath, []byte(content), os.ModePerm); err != nil {
return "", err
}
return nfoFilePath, nil
}
const (
WebDL = "WEB-DL"
DvdRip = "DVDRip"
Bluray = "BluRay"
Dvd = "DVD"
YouTube = "YouTube"
)
type TitleBuilder struct {
title string
season string
language string
quality string
resolution string
codec string
version string
dubbed bool
dualLanguage bool
enhanced bool
complete bool
extras bool
year string
episodes string
}
// Constructor
func NewTitleBuilder(title string) *TitleBuilder {
return &TitleBuilder{title: title}
}
func (t *TitleBuilder) Year(value int) *TitleBuilder {
t.year = fmt.Sprintf("(%d)", value)
return t
}
func (t *TitleBuilder) Season(value int) *TitleBuilder {
t.season = fmt.Sprintf("S%02d", value)
return t
}
func (t *TitleBuilder) EpisodeRange(first, last int) *TitleBuilder {
t.episodes = fmt.Sprintf("E%02d-E%02d", first, last)
return t
}
func (t *TitleBuilder) German() *TitleBuilder {
t.language = "German"
return t
}
func (t *TitleBuilder) Complete() *TitleBuilder {
t.complete = true
return t
}
func (t *TitleBuilder) Dubbed() *TitleBuilder {
t.dubbed = true
return t
}
func (t *TitleBuilder) Dual() *TitleBuilder {
t.dualLanguage = true
return t
}
func (t *TitleBuilder) Enhanced() *TitleBuilder {
t.enhanced = true
return t
}
func (t *TitleBuilder) Extras() *TitleBuilder {
t.extras = true
return t
}
func (t *TitleBuilder) WebDL() *TitleBuilder {
t.quality = WebDL
return t
}
func (t *TitleBuilder) DVDRip() *TitleBuilder {
t.quality = DvdRip
return t
}
func (t *TitleBuilder) Bluray() *TitleBuilder {
t.quality = Bluray
return t
}
func (t *TitleBuilder) R480() *TitleBuilder {
t.resolution = "480p"
return t
}
func (t *TitleBuilder) R576() *TitleBuilder {
t.resolution = "576p"
return t
}
func (t *TitleBuilder) R720p() *TitleBuilder {
t.resolution = "720p"
return t
}
func (t *TitleBuilder) R1080p() *TitleBuilder {
t.resolution = "1080p"
return t
}
func (t *TitleBuilder) X264() *TitleBuilder {
t.codec = "x264"
return t
}
func (t *TitleBuilder) ReleaseVersion(version string) *TitleBuilder {
t.version = fmt.Sprintf("v%s", version)
return t
}
func (t *TitleBuilder) Build() string {
var sb strings.Builder
// Replace German umlauts
title := strings.NewReplacer(
"ö", "oe",
"ä", "ae",
"ü", "ue",
).Replace(t.title)
sb.WriteString(title)
addIfTrue(&sb, t.extras, "Extras")
addIfNotEmpty(&sb, t.year, false)
hasSeason := addIfNotEmpty(&sb, t.season, false)
addIfNotEmpty(&sb, t.episodes, hasSeason)
addIfTrue(&sb, t.complete, "Complete")
addIfNotEmpty(&sb, t.language, false)
addIfTrue(&sb, t.dubbed, "Dubbed")
addIfTrue(&sb, t.dualLanguage, "DL")
addIfNotEmpty(&sb, t.quality, false)
addIfNotEmpty(&sb, t.resolution, false)
addIfTrue(&sb, t.enhanced, "Enhanced")
addIfNotEmpty(&sb, t.codec, false)
addIfNotEmpty(&sb, t.version, false)
sb.WriteString("-Roemer")
return sb.String()
}
func addIfNotEmpty(sb *strings.Builder, value string, skipDot bool) bool {
if strings.TrimSpace(value) != "" {
if !skipDot {
sb.WriteString(".")
}
sb.WriteString(value)
return true
}
return false
}
func addIfTrue(sb *strings.Builder, value bool, text string) bool {
if value {
sb.WriteString(".")
sb.WriteString(text)
return true
}
return false
}

13
task_pack_release/task.go Normal file
View File

@@ -0,0 +1,13 @@
package task_pack_release
import "os"
func PackRelease(srcPath string, dstPath string, releaseName string, archivePwd string, archiveSize string, nfoSettings *NfoCreatorSettings) error {
nfoPath, err := CreateNfo(dstPath, nfoSettings)
if err != nil {
return err
}
defer os.Remove(nfoPath)
return compress(srcPath, dstPath, releaseName, archivePwd, archiveSize, nfoPath)
}

View File

@@ -0,0 +1,18 @@
package task_pack_release
import (
"fmt"
"os"
)
func copyFile(src, dst string) error {
data, err := os.ReadFile(src)
if err != nil {
return fmt.Errorf("read error: %w", err)
}
err = os.WriteFile(dst, data, 0644)
if err != nil {
return fmt.Errorf("write error: %w", err)
}
return nil
}

View File

@@ -0,0 +1,185 @@
package tasks
import (
"bufio"
"encoding/json"
"fmt"
"os"
"os/exec"
"path/filepath"
"regexp"
"strconv"
"strings"
"time"
"github.com/roemer/goext"
)
type BlackBorderAnalyzeTask struct {
logFilePath string
cropDetectOutputRegex *regexp.Regexp
}
func NewBlackBorderAnalyzeTask(logFilePath string) *BlackBorderAnalyzeTask {
return &BlackBorderAnalyzeTask{
logFilePath: logFilePath,
cropDetectOutputRegex: regexp.MustCompile(`.*Parsed_cropdetect_0.* x1:([0-9]+) x2:([0-9]+) y1:([0-9]+) y2:([0-9]+) w:([0-9]+) h:([0-9]+) x:([0-9]+) y:([0-9]+) pts:([0-9]+) t:([0-9\.]+) limit:([0-9\.]+) crop=([0-9\:]+)`),
}
}
func (t *BlackBorderAnalyzeTask) Run(folderPath string) error {
files, err := os.ReadDir(folderPath)
if err != nil {
return fmt.Errorf("failed to read directory: %w", err)
}
for _, file := range files {
// Skip directories
if file.IsDir() {
continue
}
// Skip reencoded files
if strings.HasSuffix(file.Name(), "_2.mkv") {
continue
}
t.output(fmt.Sprintf("=== %s", file.Name()))
if err := t.processFile(filepath.Join(folderPath, file.Name())); err != nil {
return fmt.Errorf("failed to process file %s: %w", file.Name(), err)
}
}
return nil
}
func (t *BlackBorderAnalyzeTask) processFile(filePath string) error {
// Get the resolution of the video
resOutput, _, err := goext.CmdRunners.Default.RunGetOutput("ffprobe", "-v", "error", "-select_streams", "v:0", "-show_entries", "stream=width,height", "-of", "json", filePath)
if err != nil {
return fmt.Errorf("failed to run ffprobe: %w", err)
}
decoder := json.NewDecoder(strings.NewReader(resOutput))
var result struct {
Streams []struct {
Width int `json:"width"`
Height int `json:"height"`
} `json:"streams"`
}
if err := decoder.Decode(&result); err != nil {
return fmt.Errorf("failed to decode ffprobe output: %w", err)
}
videoWidth := result.Streams[0].Width
videoHeight := result.Streams[0].Height
// Execute a command and process output in real time
cmd := exec.Command("ffmpeg", "-v", "debug", "-i", filePath, "-vf", "cropdetect", "-f", "null", "-")
// Create a single pipe that combines both stdout and stderr
combinedOutput, err := cmd.StdoutPipe()
if err != nil {
return fmt.Errorf("failed to create stdout pipe: %w", err)
}
// Redirect stderr to stdout so both streams are handled together
cmd.Stderr = cmd.Stdout
// Start the command
if err := cmd.Start(); err != nil {
return fmt.Errorf("failed to start command: %w", err)
}
// Process combined output in real time with a single goroutine
go func() {
lastValue := &blackBorderAnalyzeData{}
scanner := bufio.NewScanner(combinedOutput)
for scanner.Scan() {
line := scanner.Text()
// Process each line of combined output here
value := t.processOutputLine(line)
if value != nil {
if value.x1 != lastValue.x1 || value.x2 != lastValue.x2 || value.y1 != lastValue.y1 || value.y2 != lastValue.y2 || value.w != lastValue.w || value.h != lastValue.h || value.x != lastValue.x || value.y != lastValue.y {
// output(value.String())
t.output(fmt.Sprintf("left=%d, right=%d, top=%d, bottom=%d, time:%s",
value.x1, videoWidth-value.x2, value.y1, videoHeight-value.y2, value.timeStamp))
}
lastValue = value
}
}
if err := scanner.Err(); err != nil {
fmt.Fprintf(os.Stderr, "Error reading combined output: %v\n", err)
}
}()
// Wait for the command to complete
return cmd.Wait()
}
func (t *BlackBorderAnalyzeTask) processOutputLine(line string) *blackBorderAnalyzeData {
match := t.cropDetectOutputRegex.FindStringSubmatch(line)
if match != nil {
//fmt.Println(line)
// Extracted values can be processed further
x1 := match[1]
x2 := match[2]
y1 := match[3]
y2 := match[4]
w := match[5]
h := match[6]
x := match[7]
y := match[8]
//pts := match[9]
t := match[10]
//limit := match[11]
//crop := match[12]
x1v, _ := strconv.Atoi(x1)
x2v, _ := strconv.Atoi(x2)
y1v, _ := strconv.Atoi(y1)
y2v, _ := strconv.Atoi(y2)
wv, _ := strconv.Atoi(w)
hv, _ := strconv.Atoi(h)
xv, _ := strconv.Atoi(x)
yv, _ := strconv.Atoi(y)
timeStamp, _ := strconv.ParseFloat(t, 64)
return &blackBorderAnalyzeData{
x1: x1v,
x2: x2v,
y1: y1v,
y2: y2v,
w: wv,
h: hv,
x: xv,
y: yv,
timeStamp: time.Duration(timeStamp * float64(time.Second)),
}
}
return nil
}
func (t *BlackBorderAnalyzeTask) output(value string) {
fmt.Println(value)
// Append to file
f, err := os.OpenFile(t.logFilePath, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
if err != nil {
fmt.Fprintf(os.Stderr, "Error opening file for writing: %v\n", err)
return
}
defer f.Close()
if _, err := f.WriteString(value + "\n"); err != nil {
fmt.Fprintf(os.Stderr, "Error writing to file: %v\n", err)
}
}
type blackBorderAnalyzeData struct {
x1 int
x2 int
y1 int
y2 int
w int
h int
x int
y int
timeStamp time.Duration
}
func (c blackBorderAnalyzeData) String() string {
return fmt.Sprintf("x1: %d, x2: %d, y1: %d, y2: %d, w: %d, h: %d, x: %d, y: %d, timeStamp: %s", c.x1, c.x2, c.y1, c.y2, c.w, c.h, c.x, c.y, c.timeStamp)
}

89
tasks/epic-link.go Normal file
View File

@@ -0,0 +1,89 @@
package tasks
import (
"encoding/json"
"fmt"
"net/http"
"strings"
"time"
)
type EpicLinkTask struct{}
func (t *EpicLinkTask) Run() error {
jsonContent, err := http.Get("https://api.egdata.app/free-games?country=US")
if err != nil {
return fmt.Errorf("failed fetching link")
}
defer jsonContent.Body.Close()
var parsedJson []struct {
ID string `json:"id"`
Namespace string `json:"namespace"`
Title string `json:"title"`
Tags []struct {
ID string `json:"id"`
Name string `json:"name"`
} `json:"tags"`
Giveaway struct {
ID string `json:"id"`
Namespace string `json:"namespace"`
StartDate time.Time `json:"startDate"`
EndDate time.Time `json:"endDate"`
Title string `json:"title"`
} `json:"giveaway"`
}
decoder := json.NewDecoder(jsonContent.Body)
if err := decoder.Decode(&parsedJson); err != nil {
return fmt.Errorf("failed decoding JSON: %w", err)
}
offers := []*EpicOffer{}
for _, item := range parsedJson {
if item.Giveaway.StartDate.Before(time.Now()) {
offer := &EpicOffer{
Title: item.Title,
Namespace: item.Namespace,
OfferId: item.ID,
}
for _, tag := range item.Tags {
switch tag.Name {
case "Windows":
offer.System = "PC"
offers = append(offers, offer)
case "iOS":
offer.System = "iOS"
offers = append(offers, offer)
case "Android":
offer.System = "Android"
offers = append(offers, offer)
}
}
}
}
allOffers := ""
for _, offer := range offers {
fmt.Printf("%s (%s):\n%s\n\n", offer.Title, offer.System, t.toOfferUrl(offer.ToOffer()))
allOffers += offer.ToOffer() + "&"
}
allOffers = strings.TrimSuffix(allOffers, "&")
fmt.Printf("All Offers:\n%s\n", t.toOfferUrl(allOffers))
return nil
}
func (t *EpicLinkTask) toOfferUrl(offerString string) string {
return fmt.Sprintf("https://store.epicgames.com/purchase?%s#/purchase/payment-methods", offerString)
}
type EpicOffer struct {
Title string
System string
Namespace string
OfferId string
}
func (o *EpicOffer) ToOffer() string {
return fmt.Sprintf("offers=1-%s-%s", o.Namespace, o.OfferId)
}

163
tasks/mega-account.go Normal file
View File

@@ -0,0 +1,163 @@
package tasks
import (
"bytes"
"encoding/json"
"fmt"
"io"
"net/http"
"regexp"
"time"
)
type MegaAccountTask struct{}
// jim
// fnkezq4o3a@zudpck.com
// 7xIz9GqR1CRvRpLv
func (t *MegaAccountTask) Run() error {
firstName, lastName, err := t.getRandomName()
if err != nil {
return err
}
fmt.Println("First Name:", firstName)
fmt.Println("Last Name:", lastName)
pwd, err := t.getRandomPassword()
if err != nil {
return err
}
fmt.Println("Password:", pwd)
tempMail, err := t.createTempMail()
if err != nil {
return err
}
fmt.Println("Temp Mail:", tempMail)
verificationLink, err := t.getVerificationLink(tempMail)
if err != nil {
return err
}
fmt.Println("Verification Link:", verificationLink)
return nil
}
func (t *MegaAccountTask) getRandomName() (string, string, error) {
apiUrl := "https://randomuser.me/api/"
resp, err := http.Get(apiUrl)
if err != nil {
return "", "", err
}
defer resp.Body.Close()
var jsonData struct {
Results []struct {
Name struct {
Title string `json:"title"`
First string `json:"first"`
Last string `json:"last"`
} `json:"name"`
} `json:"results"`
}
if err := json.NewDecoder(resp.Body).Decode(&jsonData); err != nil {
return "", "", err
}
return jsonData.Results[0].Name.First, jsonData.Results[0].Name.Last, nil
}
func (t *MegaAccountTask) getRandomPassword() (string, error) {
apiUrl := "https://passwordwolf.com/api/?special=off&length=16&repeat=1"
resp, err := http.Get(apiUrl)
if err != nil {
return "", err
}
defer resp.Body.Close()
var jsonData []struct {
Password string `json:"password"`
}
if err := json.NewDecoder(resp.Body).Decode(&jsonData); err != nil {
return "", err
}
return jsonData[0].Password, nil
}
func (t *MegaAccountTask) createTempMail() (string, error) {
url := "https://api.internal.temp-mail.io/api/v3/email/new"
data := map[string]int{
"min_name_length": 10,
"max_name_length": 10,
}
jsonData, err := json.Marshal(data)
if err != nil {
return "", err
}
resp, err := http.Post(url, "application/json", bytes.NewBuffer(jsonData))
if err != nil {
return "", err
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return "", err
}
var rawEmail map[string]interface{}
if err := json.Unmarshal(body, &rawEmail); err != nil {
return "", err
}
return rawEmail["email"].(string), nil
}
func (t *MegaAccountTask) getVerificationLink(email string) (string, error) {
url := fmt.Sprintf("https://api.internal.temp-mail.io/api/v3/email/%s/messages", email)
fmt.Println("Waiting for verification link...")
for {
resp, err := http.Get(url)
if err != nil {
return "", err
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return "", err
}
var emails []struct {
Id string `json:"id"`
From string `json:"from"`
Subject string `json:"subject"`
BodyText string `json:"body_text"`
BodyHTML string `json:"body_html"`
}
if err := json.Unmarshal(body, &emails); err != nil {
return "", err
}
if len(emails) == 0 {
// Retry
time.Sleep(10 * time.Second)
continue
}
emailText := emails[0].BodyText
reg := regexp.MustCompile(`(https:\/\/mega.nz\/#[a-zA-Z0-9\-_]+)`)
matches := reg.FindStringSubmatch(emailText)
if len(matches) < 2 {
return "", fmt.Errorf("verification link not found in email")
}
return matches[1], nil
}
}