Apakah ada cara yang lebih baik dari proses.cwd()
untuk menentukan direktori root berjalan node.js proses? Sesuatu seperti setara dengan Rel.root
, tapi untuk Node.js. I'm mencari sesuatu yang dapat diprediksi dan dapat diandalkan mungkin.
Ada beberapa cara untuk pendekatan ini, masing-masing dengan pro dan kontra mereka sendiri:
Dari http://nodejs.org/api/modules.html:
Ketika sebuah file dijalankan secara langsung dari Node,
memerlukan.utama
diatur kemodul
. Yang berarti bahwa anda dapat menentukan apakah berkas yang telah dijalankan langsung oleh pengujianmembutuhkan.utama === modul
Karena
modul
memberikanfilename
properti (biasanya setara dengan__filename
), entry point dari aplikasi saat ini dapat diperoleh dengan memeriksamembutuhkan.utama.filename
.
Jadi jika anda ingin direktori dasar untuk aplikasi anda, anda dapat melakukan:
var path = require('path');
var appDir = path.dirname(require.main.filename);
Ini akan bekerja sebagian besar waktu, tetapi jika anda're menjalankan aplikasi anda dengan peluncur seperti 2 atau berjalan moka tes, metode ini akan gagal.
Node memiliki global namespace objek yang disebut global
— sesuatu yang anda memasang ke objek ini akan tersedia di mana-mana di aplikasi anda. Jadi, anda index.js
(atau app.js
atau apa pun yang anda utama aplikasi file bernama), anda hanya dapat mendefinisikan variabel global:
// index.js
var path = require('path');
global.appRoot = path.resolve(__dirname);
// lib/moduleA/component1.js
require(appRoot + '/lib/moduleB/component2.js');
Bekerja secara konsisten tetapi anda harus bergantung pada sebuah variabel global, yang berarti bahwa anda dapat't dengan mudah menggunakan kembali komponen/dll.
Ini kembali direktori kerja saat ini. Tidak dapat diandalkan sama sekali, karena itu's sepenuhnya tergantung pada direktori apa proses yang diluncurkan dari:
$ cd /home/demo/
$ mkdir subdir
$ echo "console.log(process.cwd());" > subdir/demo.js
$ node subdir/demo.js
/home/demo
$ cd subdir
$ node demo.js
/home/demo/subdir
Untuk mengatasi masalah ini, saya've dibuat sebuah simpul modul yang disebut aplikasi-root-path. Penggunaan sederhana:
var appRoot = require('app-root-path');
var myModule = require(appRoot + '/lib/my-module.js');
The aplikasi-root-path modul menggunakan beberapa teknik yang berbeda untuk menentukan akar path dari aplikasi, dengan mempertimbangkan secara global modul diinstal (misalnya, jika aplikasi anda berjalan di /var/www/
tapi modul diinstal di ~/.nvm/v0.x.x/lib/node/
). Itu tidak't bekerja 100% dari waktu, tapi itu's akan bekerja di sebagian besar skenario umum.
Bekerja tanpa konfigurasi di sebagian besar keadaan. Juga menyediakan beberapa tambahan kemudahan metode (lihat halaman proyek). Con terbesar adalah bahwa hal itu tidak't bekerja jika:
node_modules
direktori (misalnya, jika anda menginstal itu secara global)Anda bisa mendapatkan sekitar ini dengan baik pengaturan APP_ROOT_PATH
lingkungan variabel, atau dengan menelepon .setPath()
pada modul, tapi dalam kasus itu, anda're mungkin lebih baik menggunakan global
metode.
Jika anda'kembali mencari cara untuk menentukan akar path dari aplikasi saat ini, salah satu solusi di atas kemungkinan akan bekerja terbaik bagi anda. Jika, di sisi lain, anda're berusaha untuk memecahkan masalah loading aplikasi modul andal, saya sangat merekomendasikan melihat ke NODE_PATH
lingkungan variabel.
Node's Modul sistem terlihat untuk modul di berbagai lokasi. Salah satu lokasi tersebut adalah di mana pun proses.env.NODE_PATH
poin. Jika anda mengatur lingkungan ini variabel, maka anda dapat memerlukan
modul dengan modul standar loader tanpa ada perubahan lain.
Misalnya, jika anda menetapkan NODE_PATH
ke /var/www/lib
, berikut akan bekerja dengan baik:
require('module2/component.js');
// ^ looks for /var/www/lib/module2/component.js
Sebuah cara yang bagus untuk melakukan ini adalah dengan menggunakan npm
:
"scripts": {
"start": "NODE_PATH=. node app.js"
}
Sekarang anda dapat memulai aplikasi anda dengan npm start
dan're emas. Saya menggabungkan ini dengan saya menegakkan node-path modul, yang mencegah sengaja memuat aplikasi tanpa NODE_PATH
set. Untuk kontrol yang lebih menegakkan variabel lingkungan, lihat checkenv.
Satu gotcha: NODE_PATH
harus diatur luar node aplikasi. Anda tidak dapat melakukan sesuatu seperti proses.env.NODE_PATH = jalan.menyelesaikan(__dirname)
karena modul loader cache daftar direktori itu akan mencari sebelum aplikasi anda berjalan.
[ditambahkan 4/6/16] Lain yang benar-benar menjanjikan modul yang mencoba untuk memecahkan masalah ini adalah bergelombang.
__dirname
isn't global; it's lokal untuk saat ini modul sehingga masing-masing file memiliki lokal sendiri, nilai yang berbeda.
Jika anda ingin direktori root dari proses yang berjalan, anda mungkin ingin menggunakan proses.cwd()
.
Jika anda ingin prediktabilitas dan keandalan, maka anda mungkin perlu untuk membuat kebutuhan aplikasi anda bahwa beberapa variabel lingkungan yang ditetapkan. Aplikasi anda mencari MY_APP_HOME
(Atau apapun) dan jika itu's ada, dan aplikasi yang ada di direktori tersebut maka semuanya baik-baik. Jika hal ini tidak terdefinisi atau direktori doesn't berisi aplikasi anda maka harus keluar dengan pesan kesalahan yang meminta pengguna untuk membuat variabel. Itu bisa diatur sebagai bagian dari proses instalasi.
Anda dapat membaca variabel lingkungan dalam node dengan sesuatu seperti proses.env.MY_ENV_VARIABLE
.
1 - membuat file dalam root proyek menyebutnya settings.js
2 - di dalam file ini menambahkan kode ini
module.exports = {
POST_MAX_SIZE : 40 , //MB
UPLOAD_MAX_FILE_SIZE: 40, //MB
PROJECT_DIR : __dirname
};
3 - dalam node_modules membuat modul baru dengan nama “setelan” dan di dalam modul index.js tulis kode ini:
module.exports = require("../../settings");
4 - dan setiap saat anda inginkan direktori proyek anda hanya menggunakan
var settings = require("settings");
settings.PROJECT_DIR;
dengan cara ini anda akan memiliki semua proyek relatif terhadap direktori file ini ;)
cara termudah untuk mendapatkan global akar (asumsi anda menggunakan NPM untuk menjalankan node.js aplikasi 'npm mulai', dll)
var appRoot = process.env.PWD;
Jika anda ingin cross-verifikasi atas
Katakanlah anda ingin untuk cross-check proses.env.PWD
dengan pengaturan anda node.js aplikasi. jika anda ingin beberapa runtime tes untuk memeriksa validitas dari proses.env.PWD
, anda bisa cross-check dengan kode ini (yang saya tulis yang tampaknya bekerja dengan baik). Anda bisa cross-check nama folder terakhir di appRoot dengan npm_package_name dalam paket anda.json file, misalnya:
var path = require('path');
var globalRoot = __dirname; //(you may have to do some substring processing if the first script you run is not in the project root, since __dirname refers to the directory that the file is in for which __dirname is called in.)
//compare the last directory in the globalRoot path to the name of the project in your package.json file
var folders = globalRoot.split(path.sep);
var packageName = folders[folders.length-1];
var pwd = process.env.PWD;
var npmPackageName = process.env.npm_package_name;
if(packageName !== npmPackageName){
throw new Error('Failed check for runtime string equality between globalRoot-bottommost directory and npm_package_name.');
}
if(globalRoot !== pwd){
throw new Error('Failed check for runtime string equality between globalRoot and process.env.PWD.');
}
anda juga dapat menggunakan NPM modul: memerlukan('aplikasi-root-path')
yang berfungsi sangat baik untuk tujuan ini
I've ditemukan ini bekerja secara konsisten untuk saya, bahkan ketika aplikasi dijalankan dari sub-folder, karena dapat dengan menguji beberapa kerangka, seperti Mocha:
process.mainModule.paths[0].split('node_modules')[0].slice(0, -1);
Mengapa ini bekerja:
Pada saat runtime node menciptakan registry dari jalan penuh dari semua file yang dimuat. Modul-modul yang dimuat pertama, dan dengan demikian di atas registri ini. Dengan memilih elemen pertama dari registri dan kembali jalan sebelum 'node_modules' direktori kita dapat menentukan akar dari aplikasi.
It's hanya satu baris kode, tapi untuk kesederhanaan's sake (ku), aku hitam kemas menjadi sebuah NPM modul:
https://www.npmjs.com/package/node-root.pddivine
Nikmati!
Semua ini "akar dirs" sebagian besar perlu untuk menyelesaikan beberapa virtual path ke real tumpukan jalan, jadi mungkin anda harus melihat path.mengatasi
?
var path= require('path');
var filePath = path.resolve('our/virtual/path.ext");
Sebenarnya, saya menemukan mungkin sepele solusi juga untuk yang paling kuat: anda cukup letakkan file berikut pada direktori root dari proyek anda: root-path.js yang memiliki kode berikut:
import * as path from 'path'
const projectRootPath = path.resolve(__dirname)
export const rootPath = projectRootPath
Teknik yang saya've ditemukan berguna ketika menggunakan express adalah dengan menambahkan kode berikut ke app.js sebelum anda lainnya rute yang ditetapkan
// set rootPath
app.use(function(req, res, next) {
req.rootPath = __dirname;
next();
});
app.use('/myroute', myRoute);
Tidak perlu menggunakan globals dan anda memiliki jalur dari direktori root sebagai properti dari objek permintaan.
Ini bekerja jika anda app.js adalah akar dari proyek anda yang, secara default, itu adalah.
Aku tahu ini sudah terlambat. Tapi kita dapat mengambil akar URL dengan dua metode
Metode 1
var path = require('path');
path.dirname(require.main.filename);
Metode 2
var path = require('path');
path.dirname(process.mainModule.filename);
Link referensi:- https://gist.github.com/geekiam/e2e3e0325abd9023d3a3
const users = require('../../../database/users'); // 👎 what you have
// OR
const users = require('$db/users'); // 👍 no matter how deep you are
const products = require('/database/products'); // 👍 alias or pathing from root directory
npm install seksi-memerlukan-simpan
memerlukan('seksi-memerlukan')
sekali pada bagian atas anda utama aplikasi file.memerlukan('seksi-memerlukan'); const router = require('/router'); const api = require('$api'); ...
.jalur
file pada root direktori proyek anda.$db = /server/database $api-v1 = /server/api/legacy $api-v2 = /server/api/v2
Di atas file utama menambahkan:
mainDir = __dirname;
Kemudian menggunakannya dalam setiap file yang anda butuhkan:
console.log('mainDir ' + mainDir);
mainDir
didefinisikan secara global, jika yang anda butuhkan hanya di saat ini file - gunakan __dirname
sebagai gantinya.main.js
, index.js
, gulpfile.js
.Tambahkan ini di suatu tempat menuju awal utama anda file aplikasi (mis. app.js):
global.__basedir = __dirname;
Ini menetapkan sebuah variabel global yang akan selalu menjadi setara dengan aplikasi anda's base dir. Gunakan hanya seperti yang lain variabel:
const yourModule = require(__basedir + '/path/to/module.js');
Sederhana...
Anda hanya dapat menambahkan direktori root path di aplikasi express variabel dan mendapatkan jalan ini dari app. Untuk ini, tambahkan app.set('direktori', __dirname);
pada anda index.js atau app.js file. Dan menggunakan req.aplikasi.mendapatkan('direktori')
untuk mendapatkan root directory path di kode anda.
process.mainModule.paths
.filter(p => !p.includes('node_modules'))
.shift()
Mendapatkan semua jalan di modul utama dan menyaring orang-orang dengan "node_modules",
kemudian mendapatkan pertama dari jalan yang tersisa klik disini. Perilaku tak terduga tidak akan melemparkan kesalahan, hanya sebuah undefined
.
Bekerja dengan baik untuk saya, bahkan ketika menelepon ie $ mocha
.