@igea/oac_backend 1.0.18 → 1.0.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@igea/oac_backend",
3
- "version": "1.0.18",
3
+ "version": "1.0.19",
4
4
  "description": "Backend service for the OAC project",
5
5
  "main": "src/index.js",
6
6
  "scripts": {
@@ -26,6 +26,7 @@
26
26
  "get-port": "7.1.0",
27
27
  "knex": "3.1.0",
28
28
  "libxmljs2": "0.37.0",
29
+ "multer": "2.0.2",
29
30
  "pg": "8.16.3",
30
31
  "strip-bom": "5.0.0"
31
32
  },
@@ -1,5 +1,8 @@
1
1
  const express = require('express');
2
+ const multer = require('multer');
2
3
  const router = express.Router();
4
+ const path = require('path');
5
+ const fs = require('fs');
3
6
  const config = require('../config')
4
7
  const configFuseki = config.fuseki || {
5
8
  "protocol": "http",
@@ -10,7 +13,88 @@ const configFuseki = config.fuseki || {
10
13
  const fusekiUrl = `${configFuseki.protocol}://${configFuseki.host}:${configFuseki.port}/${configFuseki.dataset}/sparql`;
11
14
  const axios = require('axios');
12
15
  const Fuseki = require('../models/fuseki');
16
+ const VocabParser = require('../models/vocabolaries/parser').GET_INSTANCE();
13
17
 
18
+ //---------------------------------------------------------------
19
+ const uploadFolder = path.join(__dirname, '../data/import');
20
+ if (!fs.existsSync(uploadFolder)) {
21
+ fs.mkdirSync(uploadFolder);
22
+ }
23
+ const uploadStorage = multer.diskStorage({
24
+ destination: (req, file, cb) => {
25
+ cb(null, uploadFolder); // Folder where files will be stored
26
+ },
27
+ filename: (req, file, cb) => {
28
+ cb(null, Date.now() + '-' + file.originalname);
29
+ }
30
+ });
31
+
32
+ const upload = multer({ storage: uploadStorage });
33
+ const deleteFiles = function(files){
34
+ for(let i=0; i<files.length; i++){
35
+ fs.unlink(files[i].path, (err) => {
36
+ if (err) {
37
+ console.error('Error deleting file:', files[i].path, err);
38
+ } else {
39
+ console.log('File deleted successfully:', files[i].path);
40
+ }
41
+ });
42
+ }
43
+ }
44
+ /**
45
+ * Route to upload vocabulary files
46
+ * @route POST /fuseki/upload/vocabularies
47
+ * @param {Array} files - Array of files to be uploaded
48
+ * @returns {Object} - Response object with message and file details
49
+ *
50
+ * curl -X POST -F "files=@vocabolaries.xsd" http://localhost:5000/backend/fuseki/upload/vocabularies
51
+ *
52
+ * */
53
+ router.post('/upload/vocabularies', upload.array('files'), (req, res) => {
54
+ if (!req.files || req.files.length === 0) {
55
+ return res.status(400).json({ message: 'No file uploaded' });
56
+ }
57
+
58
+ const uploadedFiles = req.files.map(file => ({
59
+ filename: file.filename,
60
+ originalname: file.originalname,
61
+ mimetype: file.mimetype,
62
+ size: file.size,
63
+ path: file.path
64
+ }));
65
+
66
+ const xmlFiles = uploadedFiles.filter(f => f.mimetype === 'application/xml' || f.mimetype === 'text/xml')
67
+ .map(file => file.valid = VocabParser.validate(file.path).status)
68
+
69
+ if(xmlFiles.length == 1) {
70
+ let xmlFile = uploadedFiles[0];
71
+ VocabParser.transform(xmlFile.path).then(terms => {
72
+ console.log(terms)
73
+ deleteFiles(uploadedFiles)
74
+ res.json({
75
+ message: 'File correctly uploaded',
76
+ files: uploadedFiles
77
+ });
78
+ }).catch(err => {
79
+ deleteFiles(uploadedFiles)
80
+ console.error('Error transforming XML:', err);
81
+ res.status(500).json({
82
+ message: 'Error transforming XML:' + err.message,
83
+ files: uploadedFiles
84
+ });
85
+ })
86
+
87
+ }else{
88
+ deleteFiles(uploadedFiles);
89
+ let message = 'Multiple XML files is not supported';
90
+ if(xmlFiles.length == 0)
91
+ message = 'No XML files uploaded';
92
+ return res.status(400).json({ message });
93
+ }
94
+
95
+ });
96
+
97
+ //---------------------------------------------------------------
14
98
  router.get('/count/entities', (req, res) => {
15
99
  const query = `
16
100
  PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
@@ -0,0 +1 @@
1
+ This folder contains data uploaded (temporary)
package/src/index.js CHANGED
@@ -10,7 +10,9 @@ const jwtLib = jwtLibFactory({
10
10
  excludePaths: [
11
11
  `/${serviceName}/auth/authenticate`,
12
12
  `/${serviceName}/auth/echo`,
13
- `/${serviceName}/health`
13
+ `/${serviceName}/health`,
14
+ `/${serviceName}/fuseki/upload/vocabularies`
15
+
14
16
  ],
15
17
  signOptions: { expiresIn: '15m' }
16
18
  });
@@ -1,7 +1,5 @@
1
1
  const fs = require('fs');
2
2
  const path = require('path');
3
- const XsltProcessor = require('xslt-processor');
4
- const {XmlParser, Xslt} = XsltProcessor;
5
3
  const libxmljs = require('libxmljs2');
6
4
  const { exec } = require('child_process');
7
5
  const stripBom = require('strip-bom').default;
@@ -39,6 +37,19 @@ class Parser{
39
37
  return xmlDoc;
40
38
  }
41
39
 
40
+ validate(xmlPath){
41
+ let result = {
42
+ status: true, message: ''
43
+ };
44
+ try{
45
+ this.parse(xmlPath);
46
+ }catch(e){
47
+ result.status = false;
48
+ result.message = `XML validation failed: ${e.message}`;
49
+ }
50
+ return result
51
+ }
52
+
42
53
  transform(xmlPath){
43
54
  return new Promise((resolve, reject) => {
44
55
  try{