How to access an asset in /private from within a package?


#1

I have a shared package that should read an JSON asset located under the /private folder of the application. But it seems as if Asset.getText() can only read assets that are located in the same package, although the docs say that /private can be accessed as well. Did anyone manage to read a file in /private from within package code?


#2

Last I checked this isn’t possible, and is by design. This was discussed in issue 1382, but I’ll quote the relevant bits here:

this is indeed by design, so that packages and applications only have access to their own assets. In theory, your package should be usable by a meteor command-line program or by another package, neither of which has a private/ directory – nor should packages have to worry about their asset filenames overlapping with application asset filenames.


#3

Ah, thanks. There are definitely use-cases for accessing the global files. In my case, I’d have a package that adds fixtures to my database, but the actual fixture contents depend on the app. I guess I’ll use the workaround provided in the thread, i.e. mapping the application’s Asset object to a GlobalAssets object. Not nice, but should work.


#4

If you need data from the global app into your package it is in general nicer to just call an object. Loading a file is a different responsibility than generating the fixtures.

Then each app using your package can use its own preferred way of storing the data. The package receives it and works on the supplied data.


#5

That’s probably right. But in my case, I want to read-in multiple files that are interconnected. That means: A main JSON file includes references to sub-ordinated JSON files, so a whole structure of JSON files is being read. An the code to do this should reside in a reusable package to avoid code duplication across my apps.


#6

Interesting approach!

Can’t you supply a function which can be run in local scope? Something like:

// in package
package.loadJSONfiles = function(path) {
  //tooling here to load the files in a uniform way
}

// in global space:
let helper = package.loadJSONfiles;
helper('/private/json/')

Other option:

// in package
package.loadJSONfiles = function(path, getFileFunction) {
  getFileFunction(path);
}

// in global space:
package.loadJSONfiles('/private/json', function(path) { loadFromPrivate(path) });

#7

That wouldn’t be JSON unless you’re proposing defining reserved key/value pairs and using some pre-processor.


#8

Yep, this might work. Thanks.


#9

I am a pragmatic programmer :slight_smile: It’s enough for me if my code understands these references.


#10

:grin: - brilliant!


#11

Hi,

I read your discussion about reading local file, but still confuse about your suggestion.

I have a Meteor app and needs to read data, from a file “/public/_assets/results/mmresults.json”, within the file “/client/controllers.js”.

I do not want to read the json file from within the file “/server/app.js” which is server side codes.

The following is my file “/public/_assets/results/mmresults.json”:

{items:[{“Draw_Date”:‘2016-01-01’,“Number_0”:“1”,“Number_1”:“1”,“Number_2”:“2”,“Nmber_3”:“3”,“Number_4”:“4”,“Number_5”:“5”},{“Draw_Date”:‘2016-01-03’,“Number_0”:“2”, “Number_1”:“2”,“Number_2”:“3”,“Nmber_3”:“4”,“Number_4”:“5”,“Number_5”:“6”}]}

The following is my codes in my “/client/controllers.js” file (client side codes):

$.getJSON("_assets/results/mmresults.json", function(data, status) {
alert("Data: " + data + "\nStatus: " + status);
});
The codes in my controllers.js file doesn’t work. Does $.getJSON work on client side or only works on server side?

Also, my app will be running on iOS 10 iPhone and the mmresults.json file needs to be resided on the iPhone and not on the Meteor server.

Please advice.

Thanks,

Brian


#12

The discussion here was about Assets.getText(). This API is available on server side only: https://docs.meteor.com/api/assets.html. I don’t have any experiences with $.getJSON(), but in principle, this should work on the client side. Please not that you should omit the public part of the path. All files and folders in public are served root-relative, i.e. to access your file, you should use the path /_assets/results/mmresults.json. I guess this is your problem.