get-package-json.js 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. /**
  2. * @author Toru Nagashima
  3. * See LICENSE file in root directory for full license.
  4. */
  5. "use strict"
  6. const fs = require("fs")
  7. const path = require("path")
  8. const Cache = require("./cache")
  9. const cache = new Cache()
  10. /**
  11. * Reads the `package.json` data in a given path.
  12. *
  13. * Don't cache the data.
  14. *
  15. * @param {string} dir - The path to a directory to read.
  16. * @returns {object|null} The read `package.json` data, or null.
  17. */
  18. function readPackageJson(dir) {
  19. const filePath = path.join(dir, "package.json")
  20. try {
  21. const text = fs.readFileSync(filePath, "utf8")
  22. const data = JSON.parse(text)
  23. if (typeof data === "object" && data !== null) {
  24. data.filePath = filePath
  25. return data
  26. }
  27. } catch (_err) {
  28. // do nothing.
  29. }
  30. return null
  31. }
  32. /**
  33. * Gets a `package.json` data.
  34. * The data is cached if found, then it's used after.
  35. *
  36. * @param {string} [startPath] - A file path to lookup.
  37. * @returns {object|null} A found `package.json` data or `null`.
  38. * This object have additional property `filePath`.
  39. */
  40. module.exports = function getPackageJson(startPath = "a.js") {
  41. const startDir = path.dirname(path.resolve(startPath))
  42. let dir = startDir
  43. let prevDir = ""
  44. let data = null
  45. do {
  46. data = cache.get(dir)
  47. if (data) {
  48. if (dir !== startDir) {
  49. cache.set(startDir, data)
  50. }
  51. return data
  52. }
  53. data = readPackageJson(dir)
  54. if (data) {
  55. cache.set(dir, data)
  56. cache.set(startDir, data)
  57. return data
  58. }
  59. // Go to next.
  60. prevDir = dir
  61. dir = path.resolve(dir, "..")
  62. } while (dir !== prevDir)
  63. cache.set(startDir, null)
  64. return null
  65. }