How to get the current directory within a meteor Smart Package - meteor

I am building a package for meteor to be published on Atmosphere and I need to get the current directory that the package is installed. I have tried process.cwd() in a file that's included in the package, but that gets the current directory of my app. The package is installed and working correctly, it just seems that the package is running in the same process as the app, hence process.cwd() is getting the current app dir. Does anyone know of a trick to get the current directory of the package?
This is what I have in the package files:
package.js
Package.on_use(function (api) {
api.use('sync-methods', 'server');
api.add_files(["lib/api_server.js"], "server");
api.add_files(["lib/api_client.js"], "client");
});
api_server.js
var cwd = process.cwd();
console.log(cwd);
This displays /home/dknell/meteor-apps/testApp

Why would you need current directory? To access a file inside the package? Then add a file as n package asset:
api.add_files(['file.txt'], 'server', {isAsset: true});
And then you can read it with Assets.getText('file.txt') in your package.

If you don't want the content, but an absolute path for another tool, you can try
var path = Npm.require('path');
var base = path.resolve('.');
var assetsBase = path.join(base, '/assets/packages/<author_smart-package-name>');
For the <author_smart-package-name> enter your package name, but if it has your meteor user name included, change the colon (:) to underscore (_)
That seems okay on OS X and Linux, probably works in windows as well.

oops, this is for files within the app, not a package. anyway maybe helpful to someone
I need to access a directory path for loading a list of files
// files in /private get built to:
// .meteorlocal/build/programs/server/assets/app/
// base path resolves to:
// .meteor/local/build/programs/server
so you need to manually add "/assets/app" to your paths.
until meteor change this at some point.
just getting to the content of a file isn't helpful if you have a directory of changing content...

Related

How can I include files from node_modules in my Next.js build so that they can be dynamically fetched?

My goal is to use the pyodide package in a Next.js project. Pyodide works like this:
import * as pyodideModule from "pyodide";
// ...
const pyodide = await pyodideModule.loadPyodide({
indexURL: "/pyodide-data",
});
The Pyodide client uses the indexURL to essentially do this:
fetch(indexURL + "/pyodide.asm.data")
fetch(indexURL + "/repodata.json")
fetch(indexURL + "/pyodide.asm.wasm")
fetch(indexURL + "/pyodide_py.tar")
fetch(indexURL + "/pyodide.asm.js")
These files are supplied in the pyodide npm package:
$ find node_modules/pyodide/py*
node_modules/pyodide/pyodide.asm.data
node_modules/pyodide/pyodide.asm.js
node_modules/pyodide/pyodide.asm.wasm
node_modules/pyodide/pyodide.d.ts
node_modules/pyodide/pyodide.js
node_modules/pyodide/pyodide.js.map
node_modules/pyodide/pyodide.mjs
node_modules/pyodide/pyodide.mjs.map
node_modules/pyodide/pyodide_py.tar
So I need to make those files part of my Next.js build.
I could do the dumb thing of manually copying the files into my public/ directory, but this means I need to ensure the versions are the same, and it pollutes my version control. I would much rather the build system do this for me.
I found this approach which uses copy-webpack-plugin to copy the files into my public/ directory, but this still pollutes my version controlled project-specific files in public/.
I've also tried copying to .next/static/pyodide-data and then telling Pyodide to load its files from the base URL "/_next/static/pyodide-data". This works, but feels very hacky - I'm using the private _next namespace.
What's the official, non-hacky Next.js way to make node_modules files available for dynamic fetching from the client?

Meteor: Could not resolve the specified constraints for this project: Unknown package

What are the constraints that Meteor is trying to resolve when it loads the packages at startup? Is it all related to versioning or is it actually looking at the code that you load with ap.use() in packages.js?
I am getting this error when I try to start up my project. I have a super-simple package file that I created with the meter create --package command. I put all of my files that make up the package into the directory that it created and moved that directory to .meteor/packages. I'm just trying to create a local package for now. Here's the contents of package.js in that directory:
Package.describe({
name: 'ammap-meteor',
summary: 'mapping library packaged for meteor ',
version: '1.0.0',
});
Package.onUse(function(api) {
api.versionsFrom('METEOR#0.9.0');
api.addFiles('ammap.js');
api.addFiles('ammap_amcharts_extension.js');
});
Package.onTest(function(api) {
api.use('tinytest');
api.use('ammap-meteor');
api.addFiles('ammap-meteor-tests.js');
});
My ammap-meteor-tests.js file is blank for the moment but it exists. Would that make a difference? And I assume you just omit the git: property from Package.onUse() for a local package, is that right?
OK, I was able to get past that error with the publish command:
meteor publish --create
So I did not succeed in making a local package (still not clear on that) but at least I can get the package to load now.

Local package asset with Meteor

I originally had an app using a private/settings.json asset. When attempting to make a package out of this app, I put that asset in packages/x:package/config/settings.json, and in the package.js's .onUse added
api.addFiles('config/settings.json', 'server', { isAsset: true });
I was using it successfully in the package as
settings = JSON.parse(Assets.getText('config/settings.json'));
until I removed private/settings.json. I now get
TypeError: Cannot read property 'token' of undefined
If I only keep private/settings.json, instead removing packages/x:package/config/settings.json (also changing from config/ to private/ in package.js, the package, etc) I get
error: File not found: private/settings.json
(How) can I have assets that are only local to the package? Alternatively, how can I include/use global assets in private/ in the package?
I think it makes sense that packages wouldn't be able to access assets in the app's private directory. Otherwise, a package could accidentally expose your app's private settings or assets.
It sounds like what you want is to share your settings.json file between the app and the package. There are several ways you could do this:
Put the settings into a second package and use it in your app and in your first package.
Have a method exported by your package called setSettings that allows the app to load its settings and then pass them into your package.
Use Meteor.settings, and launch your app with meteor --settings private/settings.json instead of getting the settings from an asset.

meteor update from 0.6.4.1 to 0.6.5

in ~/.meteor/package/ folder all package.js files has only this:
// This file is included for compatibility with the Meteor 0.6.4 package downloader.
and nothing more.
Where is the package.js code?
Thanks!
The package system has changed.
You will find the auto-generated file you're refering to under:
/packages/name_of_your_package/.build/
As for where the actual 'package.js' file is, it's under
/packages/name_of_your_package/
As per the source code that's building these files for you:
// Pre-linker versions of Meteor expect all packages in the warehouse to
// contain a file called "package.js"; they use this as part of deciding
// whether or not they need to download a new package. Because packages
// are downloaded by the *existing* version of the tools, we need to
// include this file until we're comfortable breaking "meteor update" from
// 0.6.4. (Specifically, warehouse.packageExistsInWarehouse used to check
// to see if package.js exists instead of just looking for the package
// directory.)
// XXX Remove this once we can.
builder.write("package.js", {
data: new Buffer(
("// This file is included for compatibility with the Meteor " +
"0.6.4 package downloader.\n"),
"utf8")
});
I hope this helps!

Meteor reading CSV files to populate database don't work after deploy

So I have a bunch of data that I want to load into database from CSV. I've hacked together a solution that works in local development, but when I deploy to meteor.com, it no longer works.
I'm loading the csv file in the folder /server/data/:
function readData(name){
var fs = __meteor_bootstrap__.require('fs');
var path = __meteor_bootstrap__.require('path');
var base = path.resolve('.');
var data = fs.readFileSync(path.join(base, '/server/data/', name));
return CSVToArray(data);
}
After I deploy to meteor.com, i got:
INFO Error: ENOENT, no such file or directory '/meteor/containers/98eb1286-120b-ee84-8e98-ce673fa2eab7/public/data/categories.csv'
at Object.openSync (fs.js:240:18)
at Object.readFileSync (fs.js:128:15)
at readData (app/server/models.js:10:16)
at app/server/categories.js:6:7
at /meteor/containers/98eb1286-120b-ee84-8e98-ce673fa2eab7/bundle/server/server.js:132:63
at Array.forEach (native)
at Function.<anonymous> (/meteor/containers/98eb1286-120b-ee84-8e98-ce673fa2eab7/bundle/server/underscore.js:76:11)
at /meteor/containers/98eb1286-120b-ee84-8e98-ce673fa2eab7/bundle/server/server.js:132:7
Any idea how I can get meteor to see the csv file after deployment?
I realize this question is old, but it still ranks high on certain keyword searches. So, if you're using Meteor 0.6.5+, you can use the new Assets API.
The issue is that meteor only bundles files that it knows about (ie. JS/CSS/HTML/+more depending on which packages you use) up when it deploys.
Try putting the file you need in the public directory (this directory is exempt from the above rule).
Thanks to SamuelDavis and Tom Coleman's tips. I ended up figuring out what the problem is. Turns out the bundled app is no longer formated as client, public, and server. I ended up debugging it by running meteor bundle to create a tarball. extract the tarball and took a look inside to find where the data folder is. Tom was also right that the data folder needed to be in the public folder in order to get bundled in.
It appears that the base directory is not in the same location that contains the file '/server/data/xxx.csv'.
Before you try anything else, log the base path after calling "var base = path.resolve('.'). If that value is what you expected, log the files that appear in that directory. Again if the files are what you expected, navigate into the /server folder and print out those directories and so forth.
This should pinpoint you to which folder and/or directory is missing and should indicate where you should place the CSV file in future.

Resources