@makano/rew 1.1.7 → 1.1.8

Sign up to get free protection for your applications and to get access to all the features.
package/README.md CHANGED
@@ -12,7 +12,7 @@ Rew
12
12
  <a href="https://www.npmjs.com/package/rayous"> <img src="https://img.shields.io/npm/v/@makano/rew?style=for-the-badge&logo=npm&color=b4befe&logoColor=9399b2&labelColor=181825" alt="npm version" /></a>
13
13
  </p>
14
14
 
15
- Rayous is a simple lightweight coffeescript runtime, made to simply using coffescript and revive it
15
+ Rew is a simple lightweight coffeescript runtime, made to simply using coffescript and revive it
16
16
  in the process.
17
17
 
18
18
  ## Getting Started
package/bin/ui CHANGED
Binary file
package/build.sh CHANGED
@@ -3,4 +3,6 @@ opath=./bin/ui
3
3
  if [ $1 ]; then
4
4
  opath=$1
5
5
  fi
6
- g++ ./cpp/ui.cpp -o $opath `pkg-config --cflags --libs gtk+-3.0 webkit2gtk-4.0 libwebsockets jsoncpp`
6
+ # g++ ./cpp/ui.cpp -o $opath `pkg-config --cflags --libs gtk+-3.0 webkit2gtk-4.0 libwebsockets jsoncpp`
7
+ meson build
8
+ cd build && ninja && mv ./ui $opath && cd ../ && rm -r ./build
@@ -8,12 +8,13 @@ const { watch } = require('chokidar');
8
8
  const utils = require('./utils');
9
9
  const { existsSync, readFileSync, writeFileSync, mkdirSync } = require('fs');
10
10
  const { log } = require('./log');
11
- const { compileFile, compile } = require('../modules/compiler');
11
+ const { compile } = require('../modules/compiler');
12
+ const crypto = require('crypto');
12
13
 
13
14
  yargs(hideBin(process.argv))
14
15
  .command(
15
- '$0 <file>',
16
- 'Run the specified file',
16
+ '$0 <file>',
17
+ 'Run the specified file',
17
18
  (yargs) => {
18
19
  yargs
19
20
  .positional('file', {
@@ -28,36 +29,36 @@ yargs(hideBin(process.argv))
28
29
  },
29
30
  (argv) => {
30
31
  const filePath = path.resolve(process.cwd(), argv.file);
31
- if(!existsSync(filePath)){
32
+ if (!existsSync(filePath)) {
32
33
  log('File not found:', argv.file, ':end');
33
34
  return;
34
35
  }
35
36
  const watching = [];
36
37
  const watchIt = (file) => {
37
- if(watching.includes(file)) return;
38
+ if (watching.includes(file)) return;
38
39
  watch(file).on('change', () => runIt());
39
40
  watching.push(file);
40
41
  }
41
42
  let prevFork;
42
43
  const runIt = () => {
43
- if(argv.watch) console.clear();
44
- if(prevFork && !prevFork.killed) prevFork.kill?.();
44
+ if (argv.watch) console.clear();
45
+ if (prevFork && !prevFork.killed) prevFork.kill?.();
45
46
  prevFork = fork(path.resolve(__dirname, './run.js'))
46
- .on('message', (data) => {
47
- if(argv.watch){
48
- data.forEach(file => {
49
- watchIt(file);
50
- });
51
- }
52
- }).send({ filePath, watch: argv.watch });
53
- if(argv.watch) watchIt(filePath);
47
+ .on('message', (data) => {
48
+ if (argv.watch) {
49
+ data.forEach(file => {
50
+ watchIt(file);
51
+ });
52
+ }
53
+ }).send({ filePath, watch: argv.watch });
54
+ if (argv.watch) watchIt(filePath);
54
55
  }
55
56
  runIt();
56
57
  }
57
58
  )
58
59
  .command(
59
- 'conf <command> [path] [key] [value]',
60
- 'Configuration management',
60
+ 'conf <command> [path] [key] [value]',
61
+ 'Configuration management',
61
62
  (yargs) => {
62
63
  yargs
63
64
  .positional('command', {
@@ -84,51 +85,68 @@ yargs(hideBin(process.argv))
84
85
  (argv) => {
85
86
  const { command, path, key, value } = argv;
86
87
  const result = utils.conf(command, path, key, value);
87
- if(result) console.log(result);
88
+ if (result) console.log(result);
88
89
  }
89
90
  )
90
- .command('create <path>', 'Create a new project', (yargs) => {
91
+ .command('create <path>', 'Create a new project', (yargs) => {
91
92
  yargs
92
93
  .positional('path', {
93
94
  describe: 'Path of the project to create',
94
95
  type: 'string',
95
96
  });
96
- },
97
+ },
97
98
  (argv) => {
98
99
  utils.createProject(argv.path);
99
100
  }
100
101
  )
101
- .command('ui-bin <path>', 'Build the UI bin for your own app', (yargs) => {
102
+ .command('rune-keygen <secret>', 'Generate a rune encryption key', (yargs) => {
103
+ yargs.option('secret', {
104
+ describe: 'Secret used to generate encryption key',
105
+ type: 'string'
106
+ });
107
+ }, (argv) => {
108
+ const generateEncryptionKey = (secret) => {
109
+ if (secret) {
110
+ return crypto.createHash('sha256').update(secret).digest('hex');
111
+ } else {
112
+ return crypto.randomBytes(32).toString('hex');
113
+ }
114
+ };
115
+
116
+ const encryptionKey = generateEncryptionKey(argv.secret);
117
+ console.log('Encryption Key:', encryptionKey);
118
+ })
119
+ .command('ui-bin <path>', 'Build the UI bin for your own app', (yargs) => {
102
120
  yargs
103
121
  .positional('path', {
104
122
  describe: 'Path of the output bin',
105
123
  type: 'string',
106
124
  });
107
- },
125
+ },
108
126
  (argv) => {
109
- execSync('sh '+path.resolve(__dirname, '../../../build.sh')+' '+argv.path);
127
+ execSync('sh ' + path.resolve(__dirname, '../../../build.sh') + ' ' + argv.path);
110
128
  }
111
129
  )
112
- .command('run <path | package>', 'Run an app', (yargs) => {
130
+ .command('run <path | package>', 'Run an app', (yargs) => {
113
131
  yargs
114
132
  .positional('path', {
115
133
  describe: 'Path of the app to run',
116
134
  type: 'string',
117
135
  });
118
- },
136
+ },
119
137
  (argv) => {
120
138
  utils.runApp(argv.path);
121
139
  }
122
140
  )
123
- .command('install <path>', 'Install an app', (yargs) => {
141
+ .command('install <path>', 'Install an app', (yargs) => {
124
142
  yargs
125
143
  .positional('path', {
126
144
  describe: 'Path of the app to install',
127
145
  type: 'string',
128
146
  });
129
- },
147
+ },
130
148
  async (argv) => {
131
- if(argv.path.startsWith('github:')) utils.installApp(await utils.cloneGit(argv.path), true, true);
149
+ if (argv.path.startsWith('github:')) utils.installApp(await utils.cloneGit(argv.path), true, true);
132
150
  else utils.installApp(argv.path);
133
151
  }
134
152
  )
@@ -161,7 +179,7 @@ yargs(hideBin(process.argv))
161
179
 
162
180
  function writeCompiledFile(filePath, compiledCode) {
163
181
  const dirName = outputDir ? outputDir : path.dirname(filePath);
164
- if(!existsSync(dirName)) mkdirSync(dirName, { recursive: true });
182
+ if (!existsSync(dirName)) mkdirSync(dirName, { recursive: true });
165
183
  const baseName = path.basename(filePath, path.extname(filePath));
166
184
  const newFilePath = path.join(dirName, `${baseName}.js`);
167
185
  writeFileSync(newFilePath, compiledCode, { encoding: 'utf-8' });
@@ -171,20 +189,20 @@ yargs(hideBin(process.argv))
171
189
  function processFile(filePath, importsArray) {
172
190
  const content = readFile(filePath);
173
191
  const imports = extractImports(content);
174
-
192
+
175
193
  imports.forEach(importStatement => {
176
194
  const importedFilePath = path.resolve(path.dirname(filePath), importStatement.url);
177
195
  if (!importsArray.some(importObj => importObj.url === importStatement.url)) {
178
-
179
- if(existsSync(importedFilePath)){
196
+
197
+ if (existsSync(importedFilePath)) {
180
198
  importsArray.push(importStatement);
181
199
  processFile(importedFilePath, importsArray);
182
- } else if(existsSync(importedFilePath+'.coffee')){
200
+ } else if (existsSync(importedFilePath + '.coffee')) {
183
201
  importsArray.push(importStatement);
184
- processFile(importedFilePath+'.coffee', importsArray);
185
- } else if(existsSync(importedFilePath+'.js')){
202
+ processFile(importedFilePath + '.coffee', importsArray);
203
+ } else if (existsSync(importedFilePath + '.js')) {
186
204
  importsArray.push(importStatement);
187
- processFile(importedFilePath+'.js', importsArray);
205
+ processFile(importedFilePath + '.js', importsArray);
188
206
  }
189
207
 
190
208
  }
@@ -82,6 +82,7 @@ module.exports = {
82
82
  // }
83
83
  // });
84
84
  log('Done.', ':end');
85
+ rl.close();
85
86
  }
86
87
  if (!fs.existsSync(projectPath)) {
87
88
  rl.question(logget('Package Name: '), (pkg) => {
@@ -0,0 +1,5 @@
1
+
2
+ const path = require('path');
3
+
4
+ const CONFIG_PATH = path.resolve(process.env.HOME, '.config/rew');
5
+ module.exports.CONFIG_PATH = CONFIG_PATH;
@@ -30,6 +30,10 @@ module.exports.imp = function (runPath, context) {
30
30
  let exports,
31
31
  ispkg = findPackage(filename);
32
32
 
33
+ if(filename.startsWith('@') && context.app){
34
+ filename = filename.replace('@', context.app.path);
35
+ }
36
+
33
37
  let filepath = path.resolve(path.dirname(context.module.filepath), filename);
34
38
 
35
39
  // console.log(typeof runPath);
@@ -74,7 +78,8 @@ module.exports.imp = function (runPath, context) {
74
78
  ).context.module.exports;
75
79
 
76
80
  if (ispkg) {
77
- exports = getPackage(filename)(context);
81
+ const pkg = getPackage(filename)(context);
82
+ exports = pkg._onImport ? pkg._onImport() : pkg;
78
83
  } else if (foundCache) {
79
84
 
80
85
  } else if (type == "coffee") {
@@ -0,0 +1,16 @@
1
+ const jsYaml = require("js-yaml");
2
+ const { findAppPath } = require("./findAppPath");
3
+ const path = require('path');
4
+ const { readFileSync } = require("fs");
5
+
6
+ module.exports.findAppInfo = function(filepath){
7
+ const appPath = findAppPath(path.dirname(filepath));
8
+ if(appPath){
9
+ const config = jsYaml.load(readFileSync(path.join(appPath, 'app.yaml')));
10
+ return {
11
+ path: appPath,
12
+ config
13
+ }
14
+ }
15
+ return null;
16
+ }
@@ -0,0 +1,21 @@
1
+ const path = require('path'); // Import the 'path' module
2
+ const fs = require('fs'); // Import the 'path' module
3
+
4
+ module.exports.findAppPath = (currentDir = __dirname) => {
5
+ // Check if app.yaml exists in the current directory
6
+ const appYamlPath = path.join(currentDir, 'app.yaml');
7
+ if (fs.existsSync(appYamlPath)) {
8
+ return currentDir;
9
+ }
10
+
11
+ // If not found, move up a directory level
12
+ const parentDir = path.dirname(currentDir);
13
+
14
+ // Check if we reached the root directory
15
+ if (parentDir === currentDir) {
16
+ return null; // Not found
17
+ }
18
+
19
+ // Recursively call the function on the parent directory
20
+ return module.exports.findAppPath(parentDir);
21
+ };
@@ -0,0 +1,15 @@
1
+
2
+
3
+ module.exports.seededID = function (seed) {
4
+ const charCodes = seed.split('').map(char => char.charCodeAt(0));
5
+
6
+ let result = '';
7
+ let sum = 0;
8
+
9
+ for (let i = 0; i < charCodes.length; i++) {
10
+ sum += charCodes[i];
11
+ result += String.fromCharCode((charCodes[i] + sum) % 26 + 97);
12
+ }
13
+
14
+ return result.slice(0, 12);
15
+ }
@@ -1,12 +1,12 @@
1
1
  const defaultContext = require("../const/default");
2
2
  const { execOptions } = require("../const/opt");
3
- const emitter = require("../functions/emitter");
4
3
  const { exportsFunction, pubFunction } = require("../functions/export");
5
4
  const { imp } = require("../functions/import");
6
5
  const { customRequire } = require("../functions/require");
7
6
  const fsLib = require('../functions/fs');
8
7
  const pathLib = require('../functions/path');
9
8
  const execLib = require('../functions/exec');
9
+ const { findAppInfo } = require("../misc/findAppInfo");
10
10
 
11
11
  let mainFile = "";
12
12
  const isMainFile = filepath => filepath == mainFile;
@@ -28,6 +28,7 @@ module.exports.prepareContext = function (
28
28
  meta: {},
29
29
  assert: options.import ?? {}
30
30
  },
31
+ app: findAppInfo(filepath),
31
32
  ...fsLib(filepath),
32
33
  };
33
34
  if (options.useContext) {
@@ -1,8 +1,8 @@
1
1
  const fs = require('fs');
2
2
  const jsYaml = require('js-yaml');
3
3
  const path = require('path');
4
-
5
- const CONFIG_PATH = path.resolve(process.env.HOME, '.config/rew');
4
+ const { CONFIG_PATH } = require('../const/config_path');
5
+ const { seededID } = require('../misc/seededid');
6
6
 
7
7
  const createPackageRoot = (packageName) => {
8
8
  const rootPath = path.join(CONFIG_PATH, packageName);
@@ -12,6 +12,13 @@ const createPackageRoot = (packageName) => {
12
12
 
13
13
  module.exports = (context) => ({
14
14
  CONFIG_PATH,
15
+ _onImport(){
16
+ if(context.app){
17
+ return this.create(context.app.config.package);
18
+ } else {
19
+ return this.create(seededID(path.basename(context.module.filepath).replace(/[-_/\.]/g, '')));
20
+ }
21
+ },
15
22
  create: (packageName) => {
16
23
  const rootPath = createPackageRoot(packageName);
17
24
 
@@ -0,0 +1,376 @@
1
+ const fs = require('fs');
2
+ const { v4: uuidv4 } = require('uuid');
3
+ const path = require('path');
4
+ const msgpack = require('tiny-msgpack');
5
+ const crypto = require('crypto');
6
+ const { CONFIG_PATH } = require('../const/config_path');
7
+
8
+ const ENCRYPTION_KEY = 'e6ad8b0792b9e0472ea44d1f3adfd1d503182efcce25991b05cc5ef83f307ffc';
9
+
10
+
11
+ class Change {
12
+ constructor(values) {
13
+ this.values = values;
14
+ }
15
+ }
16
+
17
+ class PopChange extends Change { };
18
+
19
+ class PushChange extends Change { };
20
+
21
+ const runePush = (...values) => new PushChange(values);
22
+ const runePop = (...values) => new PopChange(values);
23
+
24
+
25
+ function makeRef(value, props = '') {
26
+ if (!value['@rune.id']) return null;
27
+ const collection = getCollectionFromID(value['@rune.id']);
28
+ const ref = collection + '.' + value['@rune.id'];
29
+ return '@rune.ref ' + ref + props;
30
+ }
31
+
32
+ const eid = (s, diff) => s.split('')
33
+ .map(i => {
34
+ let charCode = i.charCodeAt(0) + diff;
35
+ if (charCode > 122) {
36
+ charCode -= 26;
37
+ }
38
+ return String.fromCharCode(charCode);
39
+ })
40
+ .join('');
41
+
42
+ function generateID(id, collection) {
43
+ return eid(collection, 5) + '+' + id;
44
+ }
45
+
46
+ function getCollectionFromID(id) {
47
+ return eid(id.split('+')[0], -5);
48
+ }
49
+
50
+ const createDB = (dbName, dirname, encryptionKey) => {
51
+ const dbDirPath = path.join(dirname, dbName);
52
+ const mainFilePath = path.join(dbDirPath, 'main.bin');
53
+ const algorithm = 'aes-256-ctr';
54
+
55
+ if (!fs.existsSync(dbDirPath)) {
56
+ fs.mkdirSync(dbDirPath);
57
+ }
58
+
59
+ const encrypt = (data) => {
60
+ const iv = crypto.randomBytes(16);
61
+ const cipher = crypto.createCipheriv(algorithm, Buffer.from(encryptionKey, 'hex'), iv);
62
+ const encrypted = Buffer.concat([cipher.update(data), cipher.final()]);
63
+ return Buffer.concat([iv, encrypted]);
64
+ };
65
+
66
+ const decrypt = (data) => {
67
+ const iv = data.slice(0, 16);
68
+ const encryptedData = data.slice(16);
69
+ const decipher = crypto.createDecipheriv(algorithm, Buffer.from(encryptionKey, 'hex'), iv);
70
+ const decrypted = Buffer.concat([decipher.update(encryptedData), decipher.final()]);
71
+ return decrypted;
72
+ };
73
+
74
+ const serializeData = (data) => {
75
+ return msgpack.encode(data);
76
+ };
77
+
78
+ const deserializeData = (buffer) => {
79
+ return msgpack.decode(decrypt(buffer));
80
+ };
81
+
82
+ const readMainData = () => {
83
+ if (!fs.existsSync(mainFilePath)) {
84
+ writeMainData({ collections: [], maps: [] });
85
+ }
86
+ const buffer = fs.readFileSync(mainFilePath);
87
+ return deserializeData(buffer);
88
+ };
89
+
90
+ const writeMainData = (data) => {
91
+ const buffer = encrypt(serializeData(data));
92
+ fs.writeFileSync(mainFilePath, buffer);
93
+ };
94
+
95
+ const readDataFile = (filePath) => {
96
+ const buffer = fs.readFileSync(filePath);
97
+ return deserializeData(buffer);
98
+ };
99
+
100
+ const writeDataFile = (filePath, data) => {
101
+ const buffer = encrypt(serializeData(data));
102
+ fs.writeFileSync(filePath, buffer);
103
+ };
104
+
105
+ const collection = (collectionName) => {
106
+ const collectionFilePath = path.join(dbDirPath, `${collectionName}.col`);
107
+
108
+ const create = (record) => {
109
+ const mainData = readMainData();
110
+ if (!mainData.collections.includes(collectionName)) {
111
+ mainData.collections.push(collectionName);
112
+ writeMainData(mainData);
113
+ }
114
+
115
+ let data = [];
116
+ if (fs.existsSync(collectionFilePath)) {
117
+ data = readDataFile(collectionFilePath);
118
+ }
119
+ const id = uuidv4();
120
+ record['@rune.id'] = generateID(id, collectionName);
121
+ data.push(record);
122
+ writeDataFile(collectionFilePath, data);
123
+ return record;
124
+ };
125
+
126
+ const read = (id, evaluate = true) => {
127
+ if (typeof id == "object" && '@rune.id' in id) id = id['@rune.id'];
128
+ if (!fs.existsSync(collectionFilePath)) return null;
129
+ const data = readDataFile(collectionFilePath);
130
+ const record = data.find(record => record['@rune.id'] === id);
131
+ if (record) {
132
+ return evaluateRecord(record);
133
+ }
134
+ return null;
135
+ };
136
+
137
+ const evaluateRecord = (record, prevRecord) => {
138
+ const evaluateValue = (val) => {
139
+ if (typeof val == "string" && val.startsWith('@rune.ref')) {
140
+ const ref = val.split('@rune.ref')[1].trim();
141
+ const refData = findRef(ref, false);
142
+ if (!refData) {
143
+ return null;
144
+ } else {
145
+ let value = refData;
146
+ if (refData['@rune.id']) {
147
+ value = prevRecord && prevRecord['@rune.id'] == refData['@rune.id'] ? prevRecord : evaluateRecord(refData, record);
148
+ }
149
+ return value;
150
+ }
151
+ }
152
+ if (Array.isArray(val)) {
153
+ val = val.map(i => evaluateValue(i));
154
+ }
155
+ return val;
156
+ }
157
+ for (let i in record) {
158
+ const val = record[i];
159
+ record[i] = evaluateValue(val);
160
+ }
161
+ return record;
162
+ }
163
+
164
+ const update = (caseRecord, newRecord) => {
165
+ let id;
166
+ if (typeof caseRecord === 'string') {
167
+ id = caseRecord;
168
+ } else if (typeof caseRecord === 'object') {
169
+ const data = readDataFile(collectionFilePath);
170
+ const record = data.find(record => {
171
+ for (const key in caseRecord) {
172
+ if (record[key] !== caseRecord[key]) return false;
173
+ }
174
+ return true;
175
+ });
176
+ if (record) {
177
+ id = record['@rune.id'];
178
+ } else {
179
+ return null; // No matching record found
180
+ }
181
+ }
182
+
183
+ if (!id) return null;
184
+
185
+ const data = readDataFile(collectionFilePath);
186
+ const index = data.findIndex(record => record['@rune.id'] === id);
187
+ if (index !== -1) {
188
+ const oldRecord = data[index];
189
+ for (const key in newRecord) {
190
+ const value = newRecord[key];
191
+ if (value instanceof PushChange) {
192
+ if (!oldRecord[key] || !Array.isArray(oldRecord[key])) {
193
+ oldRecord[key] = [];
194
+ }
195
+ oldRecord[key].push(...value.values);
196
+ } else if (value instanceof PopChange) {
197
+ if (oldRecord[key] && Array.isArray(oldRecord[key])) {
198
+ value.values.forEach(val => {
199
+ const index = oldRecord[key].indexOf(val);
200
+ if (index !== -1) {
201
+ oldRecord[key].splice(index, 1);
202
+ }
203
+ });
204
+ }
205
+ } else {
206
+ oldRecord[key] = value;
207
+ }
208
+ }
209
+ data[index] = oldRecord;
210
+ writeDataFile(collectionFilePath, data);
211
+ return data[index];
212
+ }
213
+ return null;
214
+ };
215
+
216
+ const find = (criteria) => {
217
+ if (typeof criteria == "string") return read(criteria);
218
+ if (!criteria || typeof criteria !== 'object') return null;
219
+
220
+ const data = readDataFile(collectionFilePath);
221
+ const record = data.find(record => {
222
+ for (const key in criteria) {
223
+ if (record[key] !== criteria[key]) return false;
224
+ }
225
+ return true;
226
+ }) || null;
227
+ if (record) {
228
+ evaluateRecord();
229
+ }
230
+ return null;
231
+ };
232
+
233
+ const remove = (id) => {
234
+ if ('@rune.id' in id) id = id['@rune.id'];
235
+ if (!fs.existsSync(collectionFilePath)) return false;
236
+ let data = readDataFile(collectionFilePath);
237
+ const index = data.findIndex(record => record['@rune.id'] === id);
238
+ if (index !== -1) {
239
+ data.splice(index, 1);
240
+ writeDataFile(collectionFilePath, data);
241
+ return true;
242
+ }
243
+ return false;
244
+ };
245
+
246
+ const list = () => {
247
+ if (!fs.existsSync(collectionFilePath)) return [];
248
+ const data = readDataFile(collectionFilePath);
249
+ return data.map(rec => evaluateRecord(rec));
250
+ };
251
+
252
+ const map = (cb, mutate = false) => {
253
+ const data = readDataFile(collectionFilePath);
254
+ const mappedData = data.map(cb);
255
+ if (mutate) {
256
+ writeDataFile(collectionFilePath, mappedData);
257
+ }
258
+ return mappedData;
259
+ };
260
+
261
+ const transform = (cb, mutate = false) => {
262
+ const data = readDataFile(collectionFilePath);
263
+ const transformedData = cb(cb);
264
+ if (mutate) {
265
+ writeDataFile(collectionFilePath, mappedData);
266
+ }
267
+ return transformedData;
268
+ }
269
+
270
+ const filter = (cb, mutate = false) => {
271
+ const data = readDataFile(collectionFilePath);
272
+ const filteredData = data.filter(cb);
273
+ if (mutate) {
274
+ writeDataFile(collectionFilePath, filteredData);
275
+ }
276
+ return filteredData;
277
+ };
278
+
279
+ const sort = (cb, mutate = false) => {
280
+ const data = readDataFile(collectionFilePath);
281
+ const sortedData = data.sort(cb);
282
+ if (mutate) {
283
+ writeDataFile(collectionFilePath, sortedData);
284
+ }
285
+ return sortedData;
286
+ };
287
+
288
+ return { create, findRef, read, update, remove, find, map, transform, filter, sort, list };
289
+ };
290
+
291
+ const findRef = (ref, evaluate = true) => {
292
+ const [name, id, ...rest] = ref.split('.');
293
+ const col = collection(name);
294
+ const record = col.read(id, evaluate);
295
+ if (rest.length === 0) return record;
296
+ let value = record;
297
+ for (const prop of rest) {
298
+ if (typeof value != "object") break;
299
+ if (!(prop in value)) return null;
300
+ value = value[prop];
301
+ }
302
+ return value;
303
+ };
304
+
305
+ const map = (mapName) => {
306
+ const mapFilePath = path.join(dbDirPath, `${mapName}.map`);
307
+
308
+ const set = (key, value) => {
309
+ const mainData = readMainData();
310
+ if (!mainData.maps.includes(mapName)) {
311
+ mainData.maps.push(mapName);
312
+ writeMainData(mainData);
313
+ }
314
+
315
+ let data = {};
316
+ if (fs.existsSync(mapFilePath)) {
317
+ data = readDataFile(mapFilePath);
318
+ }
319
+ data[key] = value;
320
+ writeDataFile(mapFilePath, data);
321
+ };
322
+
323
+ const get = (key) => {
324
+ if (!fs.existsSync(mapFilePath)) return null;
325
+ const data = readDataFile(mapFilePath);
326
+ return data[key] || null;
327
+ };
328
+
329
+ const remove = (key) => {
330
+ if (!fs.existsSync(mapFilePath)) return false;
331
+ const data = readDataFile(mapFilePath);
332
+ if (data[key]) {
333
+ delete data[key];
334
+ writeDataFile(mapFilePath, data);
335
+ return true;
336
+ }
337
+ return false;
338
+ };
339
+
340
+ const transform = (cb, mutate = false) => {
341
+ const data = readDataFile(mapFilePath);
342
+ const transformedData = cb(data);
343
+ if (mutate) {
344
+ writeDataFile(mapFilePath, transformedData);
345
+ }
346
+ return transformedData;
347
+ };
348
+
349
+ const list = () => {
350
+ if (!fs.existsSync(mapFilePath)) return {};
351
+ const data = readDataFile(mapFilePath);
352
+ return data;
353
+ };
354
+
355
+ return { set, get, remove, list, transform };
356
+ };
357
+
358
+ return { collection, findRef, makeRef, map };
359
+ };
360
+
361
+ module.exports = (context) => ({
362
+ _onImport() {
363
+ delete this.createDB;
364
+ return this;
365
+ },
366
+ db(dbname, encryptionKey) {
367
+ if (!context.app) throw new Error('rune can only be used in apps');
368
+ const pkg = path.join(CONFIG_PATH, context.app.config.package, 'db');
369
+ if (!fs.existsSync(pkg)) fs.mkdirSync(pkg, { recursive: true });
370
+ return createDB(dbname, pkg, encryptionKey || ENCRYPTION_KEY);
371
+ },
372
+ makeRef,
373
+ runePop,
374
+ runePush,
375
+ createDB
376
+ });
package/meson.build ADDED
@@ -0,0 +1,13 @@
1
+ project('rew', 'cpp',
2
+ version : '0.1',
3
+ default_options : ['warning_level=3', 'cpp_std=c++14'])
4
+
5
+ gtk3 = dependency('gtk+-3.0', method : 'pkg-config')
6
+ webkit2gtk = dependency('webkit2gtk-4.0', method : 'pkg-config')
7
+ libwebsockets = dependency('libwebsockets', method : 'pkg-config')
8
+ jsoncpp = dependency('jsoncpp', method : 'pkg-config')
9
+
10
+ executable('ui',
11
+ 'cpp/ui.cpp',
12
+ install : true,
13
+ dependencies : [gtk3, webkit2gtk, libwebsockets, jsoncpp])
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@makano/rew",
3
- "version": "1.1.7",
3
+ "version": "1.1.8",
4
4
  "description": "A simple coffescript runtime",
5
5
  "main": "lib/rew/main.js",
6
6
  "directories": {
@@ -13,6 +13,7 @@
13
13
  "lib/",
14
14
  "cpp/",
15
15
  "bin/",
16
+ "meson.build",
16
17
  "build.sh",
17
18
  "README.md"
18
19
  ],
@@ -23,7 +24,11 @@
23
24
  "type": "git",
24
25
  "url": "git+https://github.com/kevinj045/rew.git"
25
26
  },
26
- "keywords": [],
27
+ "keywords": [
28
+ "coffescript",
29
+ "rew",
30
+ "runtime"
31
+ ],
27
32
  "author": "makano",
28
33
  "license": "ISC",
29
34
  "dependencies": {
@@ -33,6 +38,8 @@
33
38
  "chalk": "^5.3.0",
34
39
  "chokidar": "^3.6.0",
35
40
  "js-yaml": "^4.1.0",
41
+ "tiny-msgpack": "^2.2.0",
42
+ "uuid": "^9.0.1",
36
43
  "vm": "^0.1.0",
37
44
  "yargs": "^17.7.2"
38
45
  },