mirror of
				https://github.com/Frooodle/Stirling-PDF.git
				synced 2025-11-01 01:21:18 +01:00 
			
		
		
		
	sync & async api
This commit is contained in:
		
							parent
							
								
									c60de02e14
								
							
						
					
					
						commit
						5203fc3605
					
				
							
								
								
									
										52
									
								
								README.md
									
									
									
									
									
								
							
							
						
						
									
										52
									
								
								README.md
									
									
									
									
									
								
							@ -2,12 +2,54 @@
 | 
			
		||||
 | 
			
		||||
This is the development repository for the new StirlingPDF backend. With the power of JS, WASM & GO this will provide almost all functionality SPDF can do currently directly on the client. For automation purposes this will still provide an API to automate your workflows.
 | 
			
		||||
 | 
			
		||||
## New/Planned Features
 | 
			
		||||
## Features
 | 
			
		||||
 | 
			
		||||
- Propper auth using passportjs
 | 
			
		||||
- Workflows & Node based editing of them.
 | 
			
		||||
- Client side PDF-Manipulation
 | 
			
		||||
- Stateful UI
 | 
			
		||||
### New
 | 
			
		||||
 | 
			
		||||
[ ] Propper auth using passportjs
 | 
			
		||||
[x] Workflows
 | 
			
		||||
[ ] Node based editing of them.
 | 
			
		||||
[x] Client side PDF-Manipulation
 | 
			
		||||
[ ] Stateful UI
 | 
			
		||||
 | 
			
		||||
### Functions
 | 
			
		||||
 | 
			
		||||
Current functions of spdf and their progress in this repo.
 | 
			
		||||
 | 
			
		||||
[x] Merge
 | 
			
		||||
[x] Split
 | 
			
		||||
[x] Rotate
 | 
			
		||||
[x] Multi-Page-Layout
 | 
			
		||||
[x] Adjust page size/scale
 | 
			
		||||
[ ] Organize
 | 
			
		||||
[ ] Change Metadata
 | 
			
		||||
[ ] Add Watermark
 | 
			
		||||
 | 
			
		||||
[ ] Remove Pages
 | 
			
		||||
[ ] Remove Blank Pages
 | 
			
		||||
[ ] Detect/Split Scanned photos
 | 
			
		||||
 | 
			
		||||
[ ] Repair
 | 
			
		||||
[ ] Compress
 | 
			
		||||
[ ] Flatten
 | 
			
		||||
[ ] Compare/Diff
 | 
			
		||||
 | 
			
		||||
[ ] Sign
 | 
			
		||||
[ ] Sign with Certificate
 | 
			
		||||
[ ] Add Password
 | 
			
		||||
[ ] Remove Password
 | 
			
		||||
[ ] Change Permissions
 | 
			
		||||
 | 
			
		||||
[ ] Image to PDF
 | 
			
		||||
[ ] Add image
 | 
			
		||||
[ ] Extract Images
 | 
			
		||||
[ ] PDF to Image
 | 
			
		||||
[ ] OCR
 | 
			
		||||
 | 
			
		||||
[ ] Convert file to PDF
 | 
			
		||||
[ ] PDF to Text/RTF
 | 
			
		||||
[ ] PDF to HTML
 | 
			
		||||
[ ] PDF to XML
 | 
			
		||||
 | 
			
		||||
## Contribute
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -1 +0,0 @@
 | 
			
		||||
// TODO: Make API endpoints available
 | 
			
		||||
							
								
								
									
										4
									
								
								index.js
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								index.js
									
									
									
									
									
								
							@ -1,4 +1,6 @@
 | 
			
		||||
 | 
			
		||||
import api from './routes/api/index.js';
 | 
			
		||||
 | 
			
		||||
import express from 'express';
 | 
			
		||||
const app = express();
 | 
			
		||||
const PORT = 8080;
 | 
			
		||||
@ -10,7 +12,7 @@ app.get('/', function (req, res, next) { // TODO: Use EJS?
 | 
			
		||||
    res.render('home.ejs');
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
// TODO: Import and server /api
 | 
			
		||||
app.use("/api/", api);
 | 
			
		||||
 
 | 
			
		||||
app.listen(PORT, function (err) {
 | 
			
		||||
    if (err) console.log(err);
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										276
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										276
									
								
								package-lock.json
									
									
									
										generated
									
									
									
								
							@ -4,6 +4,32 @@
 | 
			
		||||
  "lockfileVersion": 1,
 | 
			
		||||
  "requires": true,
 | 
			
		||||
  "dependencies": {
 | 
			
		||||
    "@pdf-lib/standard-fonts": {
 | 
			
		||||
      "version": "1.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/@pdf-lib/standard-fonts/-/standard-fonts-1.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-hU30BK9IUN/su0Mn9VdlVKsWBS6GyhVfqjwl1FjZN4TxP6cCw0jP2w7V3Hf5uX7M0AZJ16vey9yE0ny7Sa59ZA==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "pako": "^1.0.6"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "@pdf-lib/upng": {
 | 
			
		||||
      "version": "1.0.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/@pdf-lib/upng/-/upng-1.0.1.tgz",
 | 
			
		||||
      "integrity": "sha512-dQK2FUMQtowVP00mtIksrlZhdFXQZPC+taih1q4CvPZ5vqdxR/LKBaFg0oAfzd1GlHZXXSPdQfzQnt+ViGvEIQ==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "pako": "^1.0.10"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "@wasmer/wasmfs": {
 | 
			
		||||
      "version": "0.12.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/@wasmer/wasmfs/-/wasmfs-0.12.0.tgz",
 | 
			
		||||
      "integrity": "sha512-m1ftchyQ1DfSenm5XbbdGIpb6KJHH5z0gODo3IZr6lATkj4WXfX/UeBTZ0aG9YVShBp+kHLdUHvOkqjy6p/GWw==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "memfs": "3.0.4",
 | 
			
		||||
        "pako": "^1.0.11",
 | 
			
		||||
        "tar-stream": "^2.1.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "accepts": {
 | 
			
		||||
      "version": "1.3.8",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz",
 | 
			
		||||
@ -13,11 +39,31 @@
 | 
			
		||||
        "negotiator": "0.6.3"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "append-field": {
 | 
			
		||||
      "version": "1.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/append-field/-/append-field-1.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-klpgFSWLW1ZEs8svjfb7g4qWY0YS5imI82dTg+QahUvJ8YqAY0P10Uk8tTyh9ZGuYEZEMaeJYCF5BFuX552hsw=="
 | 
			
		||||
    },
 | 
			
		||||
    "array-flatten": {
 | 
			
		||||
      "version": "1.1.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz",
 | 
			
		||||
      "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg=="
 | 
			
		||||
    },
 | 
			
		||||
    "base64-js": {
 | 
			
		||||
      "version": "1.5.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz",
 | 
			
		||||
      "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA=="
 | 
			
		||||
    },
 | 
			
		||||
    "bl": {
 | 
			
		||||
      "version": "4.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "buffer": "^5.5.0",
 | 
			
		||||
        "inherits": "^2.0.4",
 | 
			
		||||
        "readable-stream": "^3.4.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "body-parser": {
 | 
			
		||||
      "version": "1.20.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.1.tgz",
 | 
			
		||||
@ -37,6 +83,28 @@
 | 
			
		||||
        "unpipe": "1.0.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "buffer": {
 | 
			
		||||
      "version": "5.7.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz",
 | 
			
		||||
      "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "base64-js": "^1.3.1",
 | 
			
		||||
        "ieee754": "^1.1.13"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "buffer-from": {
 | 
			
		||||
      "version": "1.1.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz",
 | 
			
		||||
      "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "busboy": {
 | 
			
		||||
      "version": "1.6.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz",
 | 
			
		||||
      "integrity": "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "streamsearch": "^1.1.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "bytes": {
 | 
			
		||||
      "version": "3.1.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz",
 | 
			
		||||
@ -51,6 +119,46 @@
 | 
			
		||||
        "get-intrinsic": "^1.0.2"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "concat-stream": {
 | 
			
		||||
      "version": "1.6.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz",
 | 
			
		||||
      "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "buffer-from": "^1.0.0",
 | 
			
		||||
        "inherits": "^2.0.3",
 | 
			
		||||
        "readable-stream": "^2.2.2",
 | 
			
		||||
        "typedarray": "^0.0.6"
 | 
			
		||||
      },
 | 
			
		||||
      "dependencies": {
 | 
			
		||||
        "readable-stream": {
 | 
			
		||||
          "version": "2.3.8",
 | 
			
		||||
          "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz",
 | 
			
		||||
          "integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==",
 | 
			
		||||
          "requires": {
 | 
			
		||||
            "core-util-is": "~1.0.0",
 | 
			
		||||
            "inherits": "~2.0.3",
 | 
			
		||||
            "isarray": "~1.0.0",
 | 
			
		||||
            "process-nextick-args": "~2.0.0",
 | 
			
		||||
            "safe-buffer": "~5.1.1",
 | 
			
		||||
            "string_decoder": "~1.1.1",
 | 
			
		||||
            "util-deprecate": "~1.0.1"
 | 
			
		||||
          }
 | 
			
		||||
        },
 | 
			
		||||
        "safe-buffer": {
 | 
			
		||||
          "version": "5.1.2",
 | 
			
		||||
          "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz",
 | 
			
		||||
          "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g=="
 | 
			
		||||
        },
 | 
			
		||||
        "string_decoder": {
 | 
			
		||||
          "version": "1.1.1",
 | 
			
		||||
          "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz",
 | 
			
		||||
          "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==",
 | 
			
		||||
          "requires": {
 | 
			
		||||
            "safe-buffer": "~5.1.0"
 | 
			
		||||
          }
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "content-disposition": {
 | 
			
		||||
      "version": "0.5.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz",
 | 
			
		||||
@ -74,6 +182,11 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz",
 | 
			
		||||
      "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "core-util-is": {
 | 
			
		||||
      "version": "1.0.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz",
 | 
			
		||||
      "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "debug": {
 | 
			
		||||
      "version": "2.6.9",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz",
 | 
			
		||||
@ -102,6 +215,14 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz",
 | 
			
		||||
      "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w=="
 | 
			
		||||
    },
 | 
			
		||||
    "end-of-stream": {
 | 
			
		||||
      "version": "1.4.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz",
 | 
			
		||||
      "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "once": "^1.4.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "escape-html": {
 | 
			
		||||
      "version": "1.0.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz",
 | 
			
		||||
@ -150,6 +271,11 @@
 | 
			
		||||
        "vary": "~1.1.2"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "fast-extend": {
 | 
			
		||||
      "version": "1.0.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/fast-extend/-/fast-extend-1.0.2.tgz",
 | 
			
		||||
      "integrity": "sha512-XXA9RmlPatkFKUzqVZAFth18R4Wo+Xug/S+C7YlYA3xrXwfPlW3dqNwOb4hvQo7wZJ2cNDYhrYuPzVOfHy5/uQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "finalhandler": {
 | 
			
		||||
      "version": "1.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz",
 | 
			
		||||
@ -174,6 +300,16 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz",
 | 
			
		||||
      "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q=="
 | 
			
		||||
    },
 | 
			
		||||
    "fs-constants": {
 | 
			
		||||
      "version": "1.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow=="
 | 
			
		||||
    },
 | 
			
		||||
    "fs-monkey": {
 | 
			
		||||
      "version": "0.3.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-0.3.3.tgz",
 | 
			
		||||
      "integrity": "sha512-FNUvuTAJ3CqCQb5ELn+qCbGR/Zllhf2HtwsdAtBi59s1WeCjKMT81fHcSu7dwIskqGVK+MmOrb7VOBlq3/SItw=="
 | 
			
		||||
    },
 | 
			
		||||
    "function-bind": {
 | 
			
		||||
      "version": "1.1.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz",
 | 
			
		||||
@ -225,6 +361,11 @@
 | 
			
		||||
        "safer-buffer": ">= 2.1.2 < 3"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "ieee754": {
 | 
			
		||||
      "version": "1.2.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz",
 | 
			
		||||
      "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA=="
 | 
			
		||||
    },
 | 
			
		||||
    "inherits": {
 | 
			
		||||
      "version": "2.0.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
 | 
			
		||||
@ -235,11 +376,25 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz",
 | 
			
		||||
      "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g=="
 | 
			
		||||
    },
 | 
			
		||||
    "isarray": {
 | 
			
		||||
      "version": "1.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "media-typer": {
 | 
			
		||||
      "version": "0.3.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz",
 | 
			
		||||
      "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "memfs": {
 | 
			
		||||
      "version": "3.0.4",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/memfs/-/memfs-3.0.4.tgz",
 | 
			
		||||
      "integrity": "sha512-OcZEzwX9E5AoY8SXjuAvw0DbIAYwUzV/I236I8Pqvrlv7sL/Y0E9aRCon05DhaV8pg1b32uxj76RgW0s5xjHBA==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "fast-extend": "1.0.2",
 | 
			
		||||
        "fs-monkey": "0.3.3"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "merge-descriptors": {
 | 
			
		||||
      "version": "1.0.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz",
 | 
			
		||||
@ -268,16 +423,48 @@
 | 
			
		||||
        "mime-db": "1.52.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "minimist": {
 | 
			
		||||
      "version": "1.2.8",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz",
 | 
			
		||||
      "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA=="
 | 
			
		||||
    },
 | 
			
		||||
    "mkdirp": {
 | 
			
		||||
      "version": "0.5.6",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz",
 | 
			
		||||
      "integrity": "sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "minimist": "^1.2.6"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "ms": {
 | 
			
		||||
      "version": "2.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A=="
 | 
			
		||||
    },
 | 
			
		||||
    "multer": {
 | 
			
		||||
      "version": "1.4.5-lts.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/multer/-/multer-1.4.5-lts.1.tgz",
 | 
			
		||||
      "integrity": "sha512-ywPWvcDMeH+z9gQq5qYHCCy+ethsk4goepZ45GLD63fOu0YcNecQxi64nDs3qluZB+murG3/D4dJ7+dGctcCQQ==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "append-field": "^1.0.0",
 | 
			
		||||
        "busboy": "^1.0.0",
 | 
			
		||||
        "concat-stream": "^1.5.2",
 | 
			
		||||
        "mkdirp": "^0.5.4",
 | 
			
		||||
        "object-assign": "^4.1.1",
 | 
			
		||||
        "type-is": "^1.6.4",
 | 
			
		||||
        "xtend": "^4.0.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "negotiator": {
 | 
			
		||||
      "version": "0.6.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz",
 | 
			
		||||
      "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg=="
 | 
			
		||||
    },
 | 
			
		||||
    "object-assign": {
 | 
			
		||||
      "version": "4.1.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz",
 | 
			
		||||
      "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg=="
 | 
			
		||||
    },
 | 
			
		||||
    "object-inspect": {
 | 
			
		||||
      "version": "1.13.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.0.tgz",
 | 
			
		||||
@ -291,6 +478,19 @@
 | 
			
		||||
        "ee-first": "1.1.1"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "once": {
 | 
			
		||||
      "version": "1.4.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
 | 
			
		||||
      "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "wrappy": "1"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "pako": {
 | 
			
		||||
      "version": "1.0.11",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/pako/-/pako-1.0.11.tgz",
 | 
			
		||||
      "integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw=="
 | 
			
		||||
    },
 | 
			
		||||
    "parseurl": {
 | 
			
		||||
      "version": "1.3.3",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz",
 | 
			
		||||
@ -301,6 +501,22 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz",
 | 
			
		||||
      "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "pdf-lib": {
 | 
			
		||||
      "version": "1.17.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/pdf-lib/-/pdf-lib-1.17.1.tgz",
 | 
			
		||||
      "integrity": "sha512-V/mpyJAoTsN4cnP31vc0wfNA1+p20evqqnap0KLoRUN0Yk/p3wN52DOEsL4oBFcLdb76hlpKPtzJIgo67j/XLw==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "@pdf-lib/standard-fonts": "^1.0.0",
 | 
			
		||||
        "@pdf-lib/upng": "^1.0.1",
 | 
			
		||||
        "pako": "^1.0.11",
 | 
			
		||||
        "tslib": "^1.11.1"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "process-nextick-args": {
 | 
			
		||||
      "version": "2.0.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz",
 | 
			
		||||
      "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag=="
 | 
			
		||||
    },
 | 
			
		||||
    "proxy-addr": {
 | 
			
		||||
      "version": "2.0.7",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz",
 | 
			
		||||
@ -334,6 +550,16 @@
 | 
			
		||||
        "unpipe": "1.0.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "readable-stream": {
 | 
			
		||||
      "version": "3.6.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz",
 | 
			
		||||
      "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "inherits": "^2.0.3",
 | 
			
		||||
        "string_decoder": "^1.1.1",
 | 
			
		||||
        "util-deprecate": "^1.0.1"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "safe-buffer": {
 | 
			
		||||
      "version": "5.2.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
 | 
			
		||||
@ -402,11 +628,41 @@
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz",
 | 
			
		||||
      "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "streamsearch": {
 | 
			
		||||
      "version": "1.1.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz",
 | 
			
		||||
      "integrity": "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg=="
 | 
			
		||||
    },
 | 
			
		||||
    "string_decoder": {
 | 
			
		||||
      "version": "1.3.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz",
 | 
			
		||||
      "integrity": "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "safe-buffer": "~5.2.0"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "tar-stream": {
 | 
			
		||||
      "version": "2.2.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-2.2.0.tgz",
 | 
			
		||||
      "integrity": "sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==",
 | 
			
		||||
      "requires": {
 | 
			
		||||
        "bl": "^4.0.3",
 | 
			
		||||
        "end-of-stream": "^1.4.1",
 | 
			
		||||
        "fs-constants": "^1.0.0",
 | 
			
		||||
        "inherits": "^2.0.3",
 | 
			
		||||
        "readable-stream": "^3.1.1"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "toidentifier": {
 | 
			
		||||
      "version": "1.0.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz",
 | 
			
		||||
      "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA=="
 | 
			
		||||
    },
 | 
			
		||||
    "tslib": {
 | 
			
		||||
      "version": "1.14.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
 | 
			
		||||
      "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
 | 
			
		||||
    },
 | 
			
		||||
    "type-is": {
 | 
			
		||||
      "version": "1.6.18",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz",
 | 
			
		||||
@ -416,11 +672,21 @@
 | 
			
		||||
        "mime-types": "~2.1.24"
 | 
			
		||||
      }
 | 
			
		||||
    },
 | 
			
		||||
    "typedarray": {
 | 
			
		||||
      "version": "0.0.6",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz",
 | 
			
		||||
      "integrity": "sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA=="
 | 
			
		||||
    },
 | 
			
		||||
    "unpipe": {
 | 
			
		||||
      "version": "1.0.0",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz",
 | 
			
		||||
      "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "util-deprecate": {
 | 
			
		||||
      "version": "1.0.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
 | 
			
		||||
      "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="
 | 
			
		||||
    },
 | 
			
		||||
    "utils-merge": {
 | 
			
		||||
      "version": "1.0.1",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz",
 | 
			
		||||
@ -430,6 +696,16 @@
 | 
			
		||||
      "version": "1.1.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz",
 | 
			
		||||
      "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg=="
 | 
			
		||||
    },
 | 
			
		||||
    "wrappy": {
 | 
			
		||||
      "version": "1.0.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
 | 
			
		||||
      "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="
 | 
			
		||||
    },
 | 
			
		||||
    "xtend": {
 | 
			
		||||
      "version": "4.0.2",
 | 
			
		||||
      "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz",
 | 
			
		||||
      "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ=="
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -9,7 +9,10 @@
 | 
			
		||||
  "author": "",
 | 
			
		||||
  "license": "ISC",
 | 
			
		||||
  "dependencies": {
 | 
			
		||||
    "express": "^4.18.2"
 | 
			
		||||
    "@wasmer/wasmfs": "^0.12.0",
 | 
			
		||||
    "express": "^4.18.2",
 | 
			
		||||
    "multer": "^1.4.5-lts.1",
 | 
			
		||||
    "pdf-lib": "^1.17.1"
 | 
			
		||||
  },
 | 
			
		||||
  "type": "module"
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										12
									
								
								routes/api/index.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								routes/api/index.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,12 @@
 | 
			
		||||
import express from 'express';
 | 
			
		||||
import workflow from './workflow.js';
 | 
			
		||||
 | 
			
		||||
const router = express.Router();
 | 
			
		||||
 | 
			
		||||
router.get("/", function (req, res, next) {
 | 
			
		||||
    res.status(501).json({"Error": "Unfinished Endpoint"});
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
router.use("/workflow", workflow);
 | 
			
		||||
 | 
			
		||||
export default router;
 | 
			
		||||
							
								
								
									
										125
									
								
								routes/api/workflow.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										125
									
								
								routes/api/workflow.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,125 @@
 | 
			
		||||
import express from 'express';
 | 
			
		||||
import multer from 'multer';
 | 
			
		||||
import crypto from 'crypto';
 | 
			
		||||
import stream from "stream";
 | 
			
		||||
 | 
			
		||||
import { traverseOperations } from "../../traverseOperations.js";
 | 
			
		||||
 | 
			
		||||
const activeWorkflows = {};
 | 
			
		||||
 | 
			
		||||
const router = express.Router();
 | 
			
		||||
 | 
			
		||||
router.post("/", [
 | 
			
		||||
    multer().array("files"),
 | 
			
		||||
    async (req, res, next) => {
 | 
			
		||||
        const workflow = JSON.parse(req.body.workflow);
 | 
			
		||||
        console.log("fileCount: ", req.files.length);
 | 
			
		||||
        console.log("workflow: ", workflow);
 | 
			
		||||
 | 
			
		||||
        // TODO: Validate
 | 
			
		||||
 | 
			
		||||
        let workflowID = undefined;
 | 
			
		||||
 | 
			
		||||
        const inputs = await Promise.all(req.files.map(async file => {
 | 
			
		||||
            console.log(file);
 | 
			
		||||
            return {
 | 
			
		||||
                originalFileName: file.originalname.replace(/\.[^/.]+$/, ""),
 | 
			
		||||
                fileName: file.originalname.replace(/\.[^/.]+$/, ""),
 | 
			
		||||
                buffer: new Uint8Array(await file.buffer)
 | 
			
		||||
            }
 | 
			
		||||
        }));
 | 
			
		||||
 | 
			
		||||
        // Allow option to do it synchronously and just make a long request
 | 
			
		||||
        if(req.body.async === "false") {
 | 
			
		||||
            console.log("Don't do async");
 | 
			
		||||
 | 
			
		||||
            const pdfResults = await traverseOperations(workflow.operations, inputs);
 | 
			
		||||
            downloadHandler(res, pdfResults);
 | 
			
		||||
        }
 | 
			
		||||
        else {
 | 
			
		||||
            workflowID = generateWorkflowID();
 | 
			
		||||
            activeWorkflows[workflowID] = {
 | 
			
		||||
                createdAt: Date.now(),
 | 
			
		||||
                finished: false, 
 | 
			
		||||
                eventStream: null,
 | 
			
		||||
                result: null,
 | 
			
		||||
                // TODO: When auth is implemented: owner
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            res.status(501).json({
 | 
			
		||||
                "warning": "Unfinished Endpoint",
 | 
			
		||||
                "workflowID": workflowID,
 | 
			
		||||
                "data-recieved": {
 | 
			
		||||
                    "fileCount": req.files.length,
 | 
			
		||||
                    "workflow": workflow
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
 | 
			
		||||
            traverseOperations(workflow.operations, inputs).then((pdfResults) => {
 | 
			
		||||
                activeWorkflows[workflowID].result = pdfResults;
 | 
			
		||||
                activeWorkflows[workflowID].finished = true;
 | 
			
		||||
                // TODO: Post to eventStream
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
]);
 | 
			
		||||
 | 
			
		||||
router.get("/progress/:workflowUuid", (req, res, nex) => {
 | 
			
		||||
    // TODO: Validation
 | 
			
		||||
 | 
			
		||||
    // Return current progress
 | 
			
		||||
    const workflow = activeWorkflows[req.params.workflowUuid];
 | 
			
		||||
    res.status(200).json({ createdAt: workflow.createdAt, finished: workflow.finished });
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
router.get("/progress-stream/:workflowUuid", (req, res, nex) => {
 | 
			
		||||
    // TODO: Send realtime updates
 | 
			
		||||
    res.status(501).json({"warning": "Event-Stream has not been implemented yet."});
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
router.get("/result/:workflowUuid", (req, res, nex) => {
 | 
			
		||||
    // TODO: Validation
 | 
			
		||||
 | 
			
		||||
    /* 
 | 
			
		||||
     * If workflow isn't done return error
 | 
			
		||||
     * Send file, TODO: if there are multiple outputs return as zip
 | 
			
		||||
     * If download is done, delete results / allow deletion within the next 5-60 mins
 | 
			
		||||
    */
 | 
			
		||||
    const workflow = activeWorkflows[req.params.workflowUuid];
 | 
			
		||||
    if(!workflow.finished) {
 | 
			
		||||
        res.status(202).json({ message: "Workflow hasn't finished yet. Check progress or connect to progress-steam to get notified when its done." });
 | 
			
		||||
        return
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    downloadHandler(res, workflow.result);
 | 
			
		||||
    // Delete workflow / results when done.
 | 
			
		||||
    delete activeWorkflows[req.params.workflowUuid];
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
router.post("/abort/:workflowUuid", (req, res, nex) => {
 | 
			
		||||
    // TODO: Abort workflow
 | 
			
		||||
    res.status(501).json({"warning": "Abortion has not been implemented yet."});
 | 
			
		||||
});
 | 
			
		||||
 | 
			
		||||
function generateWorkflowID() {
 | 
			
		||||
    return crypto.randomUUID();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function downloadHandler(res, pdfResults) {
 | 
			
		||||
    if(pdfResults.length > 1) {
 | 
			
		||||
        res.status(501).json({"warning": "The workflow had multiple outputs, this is not implemented yet."});
 | 
			
		||||
        // TODO: Implement ZIP
 | 
			
		||||
    }
 | 
			
		||||
    else {
 | 
			
		||||
        const readStream = new stream.PassThrough();
 | 
			
		||||
        readStream.end(pdfResults[0].buffer);
 | 
			
		||||
 | 
			
		||||
        // TODO: Implement other file types (mostly fro image & text extraction)
 | 
			
		||||
        res.set("Content-disposition", 'attachment; filename=' + pdfResults[0].fileName + ".pdf");
 | 
			
		||||
        res.set("Content-Type", "application/pdf");
 | 
			
		||||
 | 
			
		||||
        readStream.pipe(res);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export default router;
 | 
			
		||||
							
								
								
									
										206
									
								
								traverseOperations.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										206
									
								
								traverseOperations.js
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,206 @@
 | 
			
		||||
import { extractPages } from "./functions/extractPages.js";
 | 
			
		||||
import { impose } from "./functions/impose.js";
 | 
			
		||||
import { mergePDFs } from "./functions/mergePDFs.js";
 | 
			
		||||
import { rotatePages } from "./functions/rotatePDF.js";
 | 
			
		||||
import { splitPDF } from "./functions/splitPDF.js";
 | 
			
		||||
import { organizeWaitOperations } from "./public/organizeWaitOperations.js";
 | 
			
		||||
 | 
			
		||||
export async function traverseOperations(operations, input) {
 | 
			
		||||
    const waitOperations = organizeWaitOperations(operations);
 | 
			
		||||
    const results = [];
 | 
			
		||||
    await nextOperation(operations, input);
 | 
			
		||||
    return results;
 | 
			
		||||
 | 
			
		||||
    async function nextOperation(operations, input) {
 | 
			
		||||
        if(Array.isArray(operations) && operations.length == 0) { // isEmpty
 | 
			
		||||
            console.log("operation done: " + input.fileName);
 | 
			
		||||
            results.push(input);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
    
 | 
			
		||||
        for (let i = 0; i < operations.length; i++) {
 | 
			
		||||
            await computeOperation(operations[i], structuredClone(input)); // break references
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    async function computeOperation(operation, input) {
 | 
			
		||||
        switch (operation.type) {
 | 
			
		||||
            case "done":
 | 
			
		||||
                console.log("Done operation will get called if all waits are done. Skipping for now.")
 | 
			
		||||
                break;
 | 
			
		||||
            case "wait":
 | 
			
		||||
                const waitOperation = waitOperations[operation.values.id];
 | 
			
		||||
                waitOperation.input.push(input);
 | 
			
		||||
                waitOperation.waitCount--;
 | 
			
		||||
                if(waitOperation.waitCount == 0) {
 | 
			
		||||
                    await nextOperation(waitOperation.doneOperation.operations, waitOperation.input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "removeObjects":
 | 
			
		||||
                console.warn("RemoveObjects not implemented yet.")
 | 
			
		||||
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        // TODO: modfiy input
 | 
			
		||||
                        input[i].fileName += "_removedObjects";
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    // TODO: modfiy input
 | 
			
		||||
                    input.fileName += "_removedObjects";
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "extract":
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        input[i].fileName += "_extractedPages";
 | 
			
		||||
                        input[i].buffer = await extractPages(input[i].buffer, operation.values["pagesToExtractArray"]);
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    input.fileName += "_extractedPages";
 | 
			
		||||
                    input.buffer = await extractPages(input.buffer, operation.values["pagesToExtractArray"]);
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "split":
 | 
			
		||||
                // TODO: When a split goes into a wait function it might break the done condition, as it will count multiplpe times.
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        const splits = await splitPDF(input[i].buffer, operation.values["pagesToSplitAfterArray"]);
 | 
			
		||||
 | 
			
		||||
                        for (let j = 0; j < splits.length; j++) {
 | 
			
		||||
                            const split = {};
 | 
			
		||||
                            split.originalFileName = input[i].originalFileName;
 | 
			
		||||
                            split.fileName = input[i].fileName + "_split";
 | 
			
		||||
                            split.buffer = splits[j];
 | 
			
		||||
                            await nextOperation(operation.operations, split);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    const splits = await splitPDF(input.buffer, operation.values["pagesToSplitAfterArray"]);
 | 
			
		||||
 | 
			
		||||
                    for (let j = 0; j < splits.length; j++) {
 | 
			
		||||
                        const split = {};
 | 
			
		||||
                        split.originalFileName = input.originalFileName;
 | 
			
		||||
                        split.fileName = input.fileName + "_split";
 | 
			
		||||
                        split.buffer = splits[j];
 | 
			
		||||
                        await nextOperation(operation.operations, split);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "fillField":
 | 
			
		||||
                console.warn("FillField not implemented yet.")
 | 
			
		||||
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        // TODO: modfiy input
 | 
			
		||||
                        input[i].fileName += "_filledField";
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    // TODO: modfiy input
 | 
			
		||||
                    input.fileName += "_filledField";
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "extractImages":
 | 
			
		||||
                console.warn("ExtractImages not implemented yet.")
 | 
			
		||||
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        // TODO: modfiy input
 | 
			
		||||
                        input[i].fileName += "_extractedImages";
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    // TODO: modfiy input
 | 
			
		||||
                    input.fileName += "_extractedImages";
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "merge":
 | 
			
		||||
                if(Array.isArray(input) && input.length > 1) {
 | 
			
		||||
                    const inputs = input;
 | 
			
		||||
                    input = {
 | 
			
		||||
                        originalFileName: inputs.map(input => input.originalFileName).join("_and_"),
 | 
			
		||||
                        fileName: inputs.map(input => input.fileName).join("_and_") + "_merged",
 | 
			
		||||
                        buffer: await mergePDFs(inputs.map(input => input.buffer))
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    // Only one input, no need to merge
 | 
			
		||||
                    input.fileName += "_merged";
 | 
			
		||||
                }
 | 
			
		||||
                await nextOperation(operation.operations, input);
 | 
			
		||||
                break;
 | 
			
		||||
            case "transform": {
 | 
			
		||||
                console.warn("Transform not implemented yet.")
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        // TODO: modfiy input
 | 
			
		||||
                        input[i].fileName += "_transformed";
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    // TODO: modfiy input
 | 
			
		||||
                    input.fileName += "_transformed";
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
            case "extract":
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        input[i].fileName += "_extractedPages";
 | 
			
		||||
                        input[i].buffer = await extractPages(input[i].buffer, operation.values["pagesToExtractArray"]);
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    input.fileName += "_extractedPages";
 | 
			
		||||
                    input.buffer = await extractPages(input.buffer, operation.values["pagesToExtractArray"]);
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "rotate":
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        input[i].fileName += "_turned";
 | 
			
		||||
                        input[i].buffer = await rotatePages(input[i].buffer, operation.values["rotation"]);
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    input.fileName += "_turned";
 | 
			
		||||
                    input.buffer = await rotatePages(input.buffer, operation.values["rotation"]);
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "impose":
 | 
			
		||||
                if(Array.isArray(input)) {
 | 
			
		||||
                    for (let i = 0; i < input.length; i++) {
 | 
			
		||||
                        input[i].fileName += "_imposed";
 | 
			
		||||
                        input[i].buffer = await impose(input[i].buffer, operation.values["nup"], operation.values["format"]);
 | 
			
		||||
                        await nextOperation(operation.operations, input[i]);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                else {
 | 
			
		||||
                    input.fileName += "_imposed";
 | 
			
		||||
                    input.buffer = await impose(input.buffer, operation.values["nup"], operation.values["format"]);
 | 
			
		||||
                    await nextOperation(operation.operations, input);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            default:
 | 
			
		||||
                console.log("operation type unknown: ", operation.type);
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user