-
Notifications
You must be signed in to change notification settings - Fork 27.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: type hint for env
in dev mode
#67157
feat: type hint for env
in dev mode
#67157
Conversation
Co-authored-by: Shu Ding <g@shud.in>
Tests Passed |
Stats from current PRDefault BuildGeneral Overall increase
|
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
buildDuration | 17s | 14.5s | N/A |
buildDurationCached | 8.4s | 6.7s | N/A |
nodeModulesSize | 359 MB | 359 MB | |
nextStartRea..uration (ms) | 418ms | 426ms | N/A |
Client Bundles (main, webpack)
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
1780.HASH.js gzip | 167 B | 167 B | ✓ |
5453-HASH.js gzip | 35.8 kB | 35.8 kB | N/A |
7514-HASH.js gzip | 5.06 kB | 5.05 kB | N/A |
a7a62840-HASH.js gzip | 51.7 kB | 51.7 kB | N/A |
framework-HASH.js gzip | 56.7 kB | 56.7 kB | N/A |
main-app-HASH.js gzip | 221 B | 222 B | N/A |
main-HASH.js gzip | 32.3 kB | 32.3 kB | N/A |
webpack-HASH.js gzip | 1.71 kB | 1.71 kB | ✓ |
Overall change | 1.88 kB | 1.88 kB | ✓ |
Legacy Client Bundles (polyfills)
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
polyfills-HASH.js gzip | 31 kB | 31 kB | ✓ |
Overall change | 31 kB | 31 kB | ✓ |
Client Pages
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
_app-HASH.js gzip | 193 B | 193 B | ✓ |
_error-HASH.js gzip | 192 B | 192 B | ✓ |
amp-HASH.js gzip | 509 B | 510 B | N/A |
css-HASH.js gzip | 341 B | 341 B | ✓ |
dynamic-HASH.js gzip | 2.52 kB | 2.52 kB | ✓ |
edge-ssr-HASH.js gzip | 264 B | 266 B | N/A |
head-HASH.js gzip | 362 B | 363 B | N/A |
hooks-HASH.js gzip | 391 B | 390 B | N/A |
image-HASH.js gzip | 4.26 kB | 4.26 kB | ✓ |
index-HASH.js gzip | 268 B | 268 B | ✓ |
link-HASH.js gzip | 2.69 kB | 2.69 kB | N/A |
routerDirect..HASH.js gzip | 326 B | 325 B | N/A |
script-HASH.js gzip | 396 B | 397 B | N/A |
withRouter-HASH.js gzip | 320 B | 321 B | N/A |
1afbb74e6ecf..834.css gzip | 106 B | 106 B | ✓ |
Overall change | 7.89 kB | 7.89 kB | ✓ |
Client Build Manifests
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
_buildManifest.js gzip | 485 B | 483 B | N/A |
Overall change | 0 B | 0 B | ✓ |
Rendered Page Sizes
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
index.html gzip | 522 B | 524 B | N/A |
link.html gzip | 537 B | 538 B | N/A |
withRouter.html gzip | 520 B | 520 B | ✓ |
Overall change | 520 B | 520 B | ✓ |
Edge SSR bundle Size
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
edge-ssr.js gzip | 127 kB | 127 kB | ✓ |
page.js gzip | 166 kB | 166 kB | N/A |
Overall change | 127 kB | 127 kB | ✓ |
Middleware size
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
middleware-b..fest.js gzip | 660 B | 660 B | ✓ |
middleware-r..fest.js gzip | 156 B | 155 B | N/A |
middleware.js gzip | 29.5 kB | 29.5 kB | N/A |
edge-runtime..pack.js gzip | 1.03 kB | 1.03 kB | ✓ |
Overall change | 1.69 kB | 1.69 kB | ✓ |
Next Runtimes
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
app-page-exp...dev.js gzip | 183 kB | 183 kB | ✓ |
app-page-exp..prod.js gzip | 112 kB | 112 kB | ✓ |
app-page-tur..prod.js gzip | 123 kB | 123 kB | ✓ |
app-page-tur..prod.js gzip | 118 kB | 118 kB | ✓ |
app-page.run...dev.js gzip | 178 kB | 178 kB | ✓ |
app-page.run..prod.js gzip | 108 kB | 108 kB | ✓ |
app-route-ex...dev.js gzip | 23.3 kB | 23.3 kB | ✓ |
app-route-ex..prod.js gzip | 18.7 kB | 18.7 kB | ✓ |
app-route-tu..prod.js gzip | 18.7 kB | 18.7 kB | ✓ |
app-route-tu..prod.js gzip | 18.6 kB | 18.6 kB | ✓ |
app-route.ru...dev.js gzip | 24.6 kB | 24.6 kB | ✓ |
app-route.ru..prod.js gzip | 18.6 kB | 18.6 kB | ✓ |
pages-api-tu..prod.js gzip | 9.55 kB | 9.55 kB | ✓ |
pages-api.ru...dev.js gzip | 9.82 kB | 9.82 kB | ✓ |
pages-api.ru..prod.js gzip | 9.55 kB | 9.55 kB | ✓ |
pages-turbo...prod.js gzip | 21.6 kB | 21.6 kB | ✓ |
pages.runtim...dev.js gzip | 22.1 kB | 22.1 kB | ✓ |
pages.runtim..prod.js gzip | 21.6 kB | 21.6 kB | ✓ |
server.runti..prod.js gzip | 51.7 kB | 51.7 kB | N/A |
Overall change | 1.04 MB | 1.04 MB | ✓ |
build cache
vercel/next.js canary | devjiwonchoi/next.js feat/type-check-env | Change | |
---|---|---|---|
0.pack gzip | 1.67 MB | 1.67 MB | N/A |
index.pack gzip | 132 kB | 132 kB | N/A |
Overall change | 0 B | 0 B | ✓ |
Diff details
Diff for page.js
Diff too large to display
Diff for middleware.js
Diff too large to display
Diff for edge-ssr.js
Diff too large to display
Diff for image-HASH.js
@@ -1,7 +1,7 @@
(self["webpackChunk_N_E"] = self["webpackChunk_N_E"] || []).push([
[8358],
{
- /***/ 1362: /***/ (
+ /***/ 9618: /***/ (
__unused_webpack_module,
__unused_webpack_exports,
__webpack_require__
@@ -9,7 +9,7 @@
(window.__NEXT_P = window.__NEXT_P || []).push([
"/image",
function () {
- return __webpack_require__(2160);
+ return __webpack_require__(699);
},
]);
if (false) {
@@ -18,7 +18,7 @@
/***/
},
- /***/ 537: /***/ (module, exports, __webpack_require__) => {
+ /***/ 9451: /***/ (module, exports, __webpack_require__) => {
"use strict";
/* __next_internal_client_entry_do_not_use__ cjs */
Object.defineProperty(exports, "__esModule", {
@@ -40,15 +40,15 @@
__webpack_require__(3537)
);
const _head = /*#__PURE__*/ _interop_require_default._(
- __webpack_require__(7092)
+ __webpack_require__(6490)
);
- const _getimgprops = __webpack_require__(9834);
- const _imageconfig = __webpack_require__(5676);
- const _imageconfigcontextsharedruntime = __webpack_require__(387);
- const _warnonce = __webpack_require__(451);
- const _routercontextsharedruntime = __webpack_require__(5357);
+ const _getimgprops = __webpack_require__(3646);
+ const _imageconfig = __webpack_require__(535);
+ const _imageconfigcontextsharedruntime = __webpack_require__(4724);
+ const _warnonce = __webpack_require__(6321);
+ const _routercontextsharedruntime = __webpack_require__(1759);
const _imageloader = /*#__PURE__*/ _interop_require_default._(
- __webpack_require__(3945)
+ __webpack_require__(1882)
);
// This is replaced by webpack define plugin
const configEnv = {
@@ -376,7 +376,7 @@
/***/
},
- /***/ 9834: /***/ (
+ /***/ 3646: /***/ (
__unused_webpack_module,
exports,
__webpack_require__
@@ -392,9 +392,9 @@
return getImgProps;
},
});
- const _warnonce = __webpack_require__(451);
- const _imageblursvg = __webpack_require__(3547);
- const _imageconfig = __webpack_require__(5676);
+ const _warnonce = __webpack_require__(6321);
+ const _imageblursvg = __webpack_require__(8297);
+ const _imageconfig = __webpack_require__(535);
const VALID_LOADING_VALUES =
/* unused pure expression or super */ null && [
"lazy",
@@ -766,7 +766,7 @@
/***/
},
- /***/ 3547: /***/ (__unused_webpack_module, exports) => {
+ /***/ 8297: /***/ (__unused_webpack_module, exports) => {
"use strict";
/**
* A shared function, used on both client and server, to generate a SVG blur placeholder.
@@ -821,7 +821,7 @@
/***/
},
- /***/ 6850: /***/ (
+ /***/ 973: /***/ (
__unused_webpack_module,
exports,
__webpack_require__
@@ -848,10 +848,10 @@
},
});
const _interop_require_default = __webpack_require__(1478);
- const _getimgprops = __webpack_require__(9834);
- const _imagecomponent = __webpack_require__(537);
+ const _getimgprops = __webpack_require__(3646);
+ const _imagecomponent = __webpack_require__(9451);
const _imageloader = /*#__PURE__*/ _interop_require_default._(
- __webpack_require__(3945)
+ __webpack_require__(1882)
);
function getImageProps(imgProps) {
const { props } = (0, _getimgprops.getImgProps)(imgProps, {
@@ -883,7 +883,7 @@
/***/
},
- /***/ 3945: /***/ (__unused_webpack_module, exports) => {
+ /***/ 1882: /***/ (__unused_webpack_module, exports) => {
"use strict";
Object.defineProperty(exports, "__esModule", {
@@ -918,7 +918,7 @@
/***/
},
- /***/ 2160: /***/ (
+ /***/ 699: /***/ (
__unused_webpack_module,
__webpack_exports__,
__webpack_require__
@@ -935,8 +935,8 @@
// EXTERNAL MODULE: ./node_modules/.pnpm/react@19.0.0-rc-6230622a1a-20240610/node_modules/react/jsx-runtime.js
var jsx_runtime = __webpack_require__(898);
- // EXTERNAL MODULE: ./node_modules/.pnpm/next@file+..+main-repo+packages+next+next-packed.tgz_react-dom@19.0.0-rc-6230622a1a-20240610__zehaskxadtwcczqqbmt6koh6bq/node_modules/next/image.js
- var next_image = __webpack_require__(6793);
+ // EXTERNAL MODULE: ./node_modules/.pnpm/next@file+..+diff-repo+packages+next+next-packed.tgz_react-dom@19.0.0-rc-6230622a1a-20240610__uulzbengwsfwhwaa2ambxampcy/node_modules/next/image.js
+ var next_image = __webpack_require__(1428);
var image_default = /*#__PURE__*/ __webpack_require__.n(next_image); // CONCATENATED MODULE: ./pages/nextjs.png
/* harmony default export */ const nextjs = {
src: "/_next/static/media/nextjs.cae0b805.png",
@@ -966,12 +966,12 @@
/***/
},
- /***/ 6793: /***/ (
+ /***/ 1428: /***/ (
module,
__unused_webpack_exports,
__webpack_require__
) => {
- module.exports = __webpack_require__(6850);
+ module.exports = __webpack_require__(973);
/***/
},
@@ -981,7 +981,7 @@
/******/ var __webpack_exec__ = (moduleId) =>
__webpack_require__((__webpack_require__.s = moduleId));
/******/ __webpack_require__.O(0, [2888, 9774, 179], () =>
- __webpack_exec__(1362)
+ __webpack_exec__(9618)
);
/******/ var __webpack_exports__ = __webpack_require__.O();
/******/ _N_E = __webpack_exports__;
Diff for main-HASH.js
Diff too large to display
Diff for server.runtime.prod.js
@@ -1,4 +1,4 @@
-(()=>{var e={"../next-env/dist/index.js":(e,t,r)=>{(()=>{var t={383:e=>{"use strict";e.exports.j=function(e){let t=e.ignoreProcessEnv?{}:process.env;for(let r in e.parsed){let i=Object.prototype.hasOwnProperty.call(t,r)?t[r]:e.parsed[r];e.parsed[r]=(function e(t,r,i){let n=function(e,t){let r=Array.from(e.matchAll(t));return r.length>0?r.slice(-1)[0].index:-1}(t,/(?!(?<=\\))\$/g);if(-1===n)return t;let s=t.slice(n).match(/((?!(?<=\\))\${?([\w]+)(?::-([^}\\]*))?}?)/);if(null!=s){let[,n,a,o]=s;return e(t.replace(n,r[a]||o||i.parsed[a]||""),r,i)}return t})(i,t,e).replace(/\\\$/g,"$")}for(let r in e.parsed)t[r]=e.parsed[r];return e}},234:(e,t,r)=>{let i=r(147),n=r(17),s=r(37),a=r(113),o=r(803).version,l=/(?:^|^)\s*(?:export\s+)?([\w.-]+)(?:\s*=\s*?|:\s+?)(\s*'(?:\\'|[^'])*'|\s*"(?:\\"|[^"])*"|\s*`(?:\\`|[^`])*`|[^#\r\n]+)?\s*(?:#.*)?(?:$|$)/gm;function h(e){console.log(`[dotenv@${o}][DEBUG] ${e}`)}function d(e){return e&&e.DOTENV_KEY&&e.DOTENV_KEY.length>0?e.DOTENV_KEY:process.env.DOTENV_KEY&&process.env.DOTENV_KEY.length>0?process.env.DOTENV_KEY:""}function u(e){let t=n.resolve(process.cwd(),".env");return e&&e.path&&e.path.length>0&&(t=e.path),t.endsWith(".vault")?t:`${t}.vault`}let c={configDotenv:function(e){let t=n.resolve(process.cwd(),".env"),r="utf8",a=!!(e&&e.debug);if(e){if(null!=e.path){var o;t="~"===(o=e.path)[0]?n.join(s.homedir(),o.slice(1)):o}null!=e.encoding&&(r=e.encoding)}try{let n=c.parse(i.readFileSync(t,{encoding:r})),s=process.env;return e&&null!=e.processEnv&&(s=e.processEnv),c.populate(s,n,e),{parsed:n}}catch(e){return a&&h(`Failed to load ${t} ${e.message}`),{error:e}}},_configVault:function(e){console.log(`[dotenv@${o}][INFO] Loading env from encrypted .env.vault`);let t=c._parseVault(e),r=process.env;return e&&null!=e.processEnv&&(r=e.processEnv),c.populate(r,t,e),{parsed:t}},_parseVault:function(e){let t;let r=u(e),i=c.configDotenv({path:r});if(!i.parsed)throw Error(`MISSING_DATA: Cannot parse ${r} for an unknown reason`);let n=d(e).split(","),s=n.length;for(let e=0;e<s;e++)try{let r=n[e].trim(),s=function(e,t){let r;try{r=new URL(t)}catch(e){if("ERR_INVALID_URL"===e.code)throw Error("INVALID_DOTENV_KEY: Wrong format. Must be in valid uri format like dotenv://:key_1234@dotenv.org/vault/.env.vault?environment=development");throw e}let i=r.password;if(!i)throw Error("INVALID_DOTENV_KEY: Missing key part");let n=r.searchParams.get("environment");if(!n)throw Error("INVALID_DOTENV_KEY: Missing environment part");let s=`DOTENV_VAULT_${n.toUpperCase()}`,a=e.parsed[s];if(!a)throw Error(`NOT_FOUND_DOTENV_ENVIRONMENT: Cannot locate environment ${s} in your .env.vault file.`);return{ciphertext:a,key:i}}(i,r);t=c.decrypt(s.ciphertext,s.key);break}catch(t){if(e+1>=s)throw t}return c.parse(t)},config:function(e){let t=u(e);if(0===d(e).length)return c.configDotenv(e);if(!i.existsSync(t)){var r;return r=`You set DOTENV_KEY but you are missing a .env.vault file at ${t}. Did you forget to build it?`,console.log(`[dotenv@${o}][WARN] ${r}`),c.configDotenv(e)}return c._configVault(e)},decrypt:function(e,t){let r=Buffer.from(t.slice(-64),"hex"),i=Buffer.from(e,"base64"),n=i.slice(0,12),s=i.slice(-16);i=i.slice(12,-16);try{let e=a.createDecipheriv("aes-256-gcm",r,n);return e.setAuthTag(s),`${e.update(i)}${e.final()}`}catch(i){let e=i instanceof RangeError,t="Invalid key length"===i.message,r="Unsupported state or unable to authenticate data"===i.message;if(e||t)throw Error("INVALID_DOTENV_KEY: It must be 64 characters long (or more)");if(r)throw Error("DECRYPTION_FAILED: Please check your DOTENV_KEY");throw console.error("Error: ",i.code),console.error("Error: ",i.message),i}},parse:function(e){let t;let r={},i=e.toString();for(i=i.replace(/\r\n?/gm,"\n");null!=(t=l.exec(i));){let e=t[1],i=t[2]||"",n=(i=i.trim())[0];i=i.replace(/^(['"`])([\s\S]*)\1$/gm,"$2"),'"'===n&&(i=(i=i.replace(/\\n/g,"\n")).replace(/\\r/g,"\r")),r[e]=i}return r},populate:function(e,t,r={}){let i=!!(r&&r.debug),n=!!(r&&r.override);if("object"!=typeof t)throw Error("OBJECT_REQUIRED: Please check the processEnv argument being passed to populate");for(let r of Object.keys(t))Object.prototype.hasOwnProperty.call(e,r)?(!0===n&&(e[r]=t[r]),i&&(!0===n?h(`"${r}" is already defined and WAS overwritten`):h(`"${r}" is already defined and was NOT overwritten`))):e[r]=t[r]}};e.exports.configDotenv=c.configDotenv,e.exports._configVault=c._configVault,e.exports._parseVault=c._parseVault,e.exports.config=c.config,e.exports.decrypt=c.decrypt,e.exports.parse=c.parse,e.exports.populate=c.populate,e.exports=c},113:e=>{"use strict";e.exports=r("crypto")},147:e=>{"use strict";e.exports=r("fs")},37:e=>{"use strict";e.exports=r("os")},17:e=>{"use strict";e.exports=r("path")},803:e=>{"use strict";e.exports=JSON.parse('{"name":"dotenv","version":"16.3.1","description":"Loads environment variables from .env file","main":"lib/main.js","types":"lib/main.d.ts","exports":{".":{"types":"./lib/main.d.ts","require":"./lib/main.js","default":"./lib/main.js"},"./config":"./config.js","./config.js":"./config.js","./lib/env-options":"./lib/env-options.js","./lib/env-options.js":"./lib/env-options.js","./lib/cli-options":"./lib/cli-options.js","./lib/cli-options.js":"./lib/cli-options.js","./package.json":"./package.json"},"scripts":{"dts-check":"tsc --project tests/types/tsconfig.json","lint":"standard","lint-readme":"standard-markdown","pretest":"npm run lint && npm run dts-check","test":"tap tests/*.js --100 -Rspec","prerelease":"npm test","release":"standard-version"},"repository":{"type":"git","url":"git://github.com/motdotla/dotenv.git"},"funding":"https://github.com/motdotla/dotenv?sponsor=1","keywords":["dotenv","env",".env","environment","variables","config","settings"],"readmeFilename":"README.md","license":"BSD-2-Clause","devDependencies":{"@definitelytyped/dtslint":"^0.0.133","@types/node":"^18.11.3","decache":"^4.6.1","sinon":"^14.0.1","standard":"^17.0.0","standard-markdown":"^7.1.0","standard-version":"^9.5.0","tap":"^16.3.0","tar":"^6.1.11","typescript":"^4.8.4"},"engines":{"node":">=12"},"browser":{"fs":false}}')}},i={};function n(e){var r=i[e];if(void 0!==r)return r.exports;var s=i[e]={exports:{}},a=!0;try{t[e](s,s.exports,n),a=!1}finally{a&&delete i[e]}return s.exports}n.n=e=>{var t=e&&e.__esModule?()=>e.default:()=>e;return n.d(t,{a:t}),t},n.d=(e,t)=>{for(var r in t)n.o(t,r)&&!n.o(e,r)&&Object.defineProperty(e,r,{enumerable:!0,get:t[r]})},n.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t),n.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.ab=__dirname+"/";var s={};(()=>{"use strict";let e,t;n.r(s),n.d(s,{initialEnv:()=>e,updateInitialEnv:()=>d,processEnv:()=>c,resetEnv:()=>p,loadEnvConfig:()=>f});var r=n(147);n.n(r);var i=n(17);n.n(i);var a=n(234);n.n(a);var o=n(383);let l=[],h=[];function d(t){Object.assign(e||{},t)}function u(e){Object.keys(process.env).forEach(t=>{t.startsWith("__NEXT_PRIVATE")||void 0!==e[t]&&""!==e[t]||delete process.env[t]}),Object.entries(e).forEach(([e,t])=>{process.env[e]=t})}function c(t,r,n=console,s=!1,l){var d;if(e||(e=Object.assign({},process.env)),!s&&(process.env.__NEXT_PROCESSED_ENV||0===t.length))return process.env;process.env.__NEXT_PROCESSED_ENV="true";let u=Object.assign({},e),p={};for(let e of t)try{let t={};for(let r of(t.parsed=a.parse(e.contents),(t=(0,o.j)(t)).parsed&&!h.some(t=>t.contents===e.contents&&t.path===e.path)&&(null==l||l(e.path)),Object.keys(t.parsed||{})))void 0===p[r]&&void 0===u[r]&&(p[r]=null===(d=t.parsed)||void 0===d?void 0:d[r])}catch(t){n.error(`Failed to load env from ${i.join(r||"",e.path)}`,t)}return Object.assign(process.env,p)}function p(){e&&u(e)}function f(n,s,a=console,o=!1,d){if(e||(e=Object.assign({},process.env)),t&&!o)return{combinedEnv:t,loadedEnvFiles:l};u(e),h=l,l=[];let p=s?"development":"production";for(let e of[`.env.${p}.local`,"test"!==p&&".env.local",`.env.${p}`,".env"].filter(Boolean)){let t=i.join(n,e);try{if(!r.statSync(t).isFile())continue;let i=r.readFileSync(t,"utf8");l.push({path:e,contents:i})}catch(t){"ENOENT"!==t.code&&a.error(`Failed to load env from ${e}`,t)}}return{combinedEnv:t=c(l,n,a,o,d),loadedEnvFiles:l}}})(),e.exports=s})()},"./dist/compiled/@edge-runtime/cookies/index.js":e=>{"use strict";var t=Object.defineProperty,r=Object.getOwnPropertyDescriptor,i=Object.getOwnPropertyNames,n=Object.prototype.hasOwnProperty,s={};function a(e){var t;let r=["path"in e&&e.path&&`Path=${e.path}`,"expires"in e&&(e.expires||0===e.expires)&&`Expires=${("number"==typeof e.expires?new Date(e.expires):e.expires).toUTCString()}`,"maxAge"in e&&"number"==typeof e.maxAge&&`Max-Age=${e.maxAge}`,"domain"in e&&e.domain&&`Domain=${e.domain}`,"secure"in e&&e.secure&&"Secure","httpOnly"in e&&e.httpOnly&&"HttpOnly","sameSite"in e&&e.sameSite&&`SameSite=${e.sameSite}`,"partitioned"in e&&e.partitioned&&"Partitioned","priority"in e&&e.priority&&`Priority=${e.priority}`].filter(Boolean),i=`${e.name}=${encodeURIComponent(null!=(t=e.value)?t:"")}`;return 0===r.length?i:`${i}; ${r.join("; ")}`}function o(e){let t=new Map;for(let r of e.split(/; */)){if(!r)continue;let e=r.indexOf("=");if(-1===e){t.set(r,"true");continue}let[i,n]=[r.slice(0,e),r.slice(e+1)];try{t.set(i,decodeURIComponent(null!=n?n:"true"))}catch{}}return t}function l(e){var t,r;if(!e)return;let[[i,n],...s]=o(e),{domain:a,expires:l,httponly:u,maxage:c,path:p,samesite:f,secure:m,partitioned:g,priority:v}=Object.fromEntries(s.map(([e,t])=>[e.toLowerCase(),t]));return function(e){let t={};for(let r in e)e[r]&&(t[r]=e[r]);return t}({name:i,value:decodeURIComponent(n),domain:a,...l&&{expires:new Date(l)},...u&&{httpOnly:!0},..."string"==typeof c&&{maxAge:Number(c)},path:p,...f&&{sameSite:h.includes(t=(t=f).toLowerCase())?t:void 0},...m&&{secure:!0},...v&&{priority:d.includes(r=(r=v).toLowerCase())?r:void 0},...g&&{partitioned:!0}})}((e,r)=>{for(var i in r)t(e,i,{get:r[i],enumerable:!0})})(s,{RequestCookies:()=>u,ResponseCookies:()=>c,parseCookie:()=>o,parseSetCookie:()=>l,stringifyCookie:()=>a}),e.exports=((e,s,a,o)=>{if(s&&"object"==typeof s||"function"==typeof s)for(let l of i(s))n.call(e,l)||l===a||t(e,l,{get:()=>s[l],enumerable:!(o=r(s,l))||o.enumerable});return e})(t({},"__esModule",{value:!0}),s);var h=["strict","lax","none"],d=["low","medium","high"],u=class{constructor(e){this._parsed=new Map,this._headers=e;let t=e.get("cookie");if(t)for(let[e,r]of o(t))this._parsed.set(e,{name:e,value:r})}[Symbol.iterator](){return this._parsed[Symbol.iterator]()}get size(){return this._parsed.size}get(...e){let t="string"==typeof e[0]?e[0]:e[0].name;return this._parsed.get(t)}getAll(...e){var t;let r=Array.from(this._parsed);if(!e.length)return r.map(([e,t])=>t);let i="string"==typeof e[0]?e[0]:null==(t=e[0])?void 0:t.name;return r.filter(([e])=>e===i).map(([e,t])=>t)}has(e){return this._parsed.has(e)}set(...e){let[t,r]=1===e.length?[e[0].name,e[0].value]:e,i=this._parsed;return i.set(t,{name:t,value:r}),this._headers.set("cookie",Array.from(i).map(([e,t])=>a(t)).join("; ")),this}delete(e){let t=this._parsed,r=Array.isArray(e)?e.map(e=>t.delete(e)):t.delete(e);return this._headers.set("cookie",Array.from(t).map(([e,t])=>a(t)).join("; ")),r}clear(){return this.delete(Array.from(this._parsed.keys())),this}[Symbol.for("edge-runtime.inspect.custom")](){return`RequestCookies ${JSON.stringify(Object.fromEntries(this._parsed))}`}toString(){return[...this._parsed.values()].map(e=>`${e.name}=${encodeURIComponent(e.value)}`).join("; ")}},c=class{constructor(e){var t,r,i;this._parsed=new Map,this._headers=e;let n=null!=(i=null!=(r=null==(t=e.getSetCookie)?void 0:t.call(e))?r:e.get("set-cookie"))?i:[];for(let e of Array.isArray(n)?n:function(e){if(!e)return[];var t,r,i,n,s,a=[],o=0;function l(){for(;o<e.length&&/\s/.test(e.charAt(o));)o+=1;return o<e.length}for(;o<e.length;){for(t=o,s=!1;l();)if(","===(r=e.charAt(o))){for(i=o,o+=1,l(),n=o;o<e.length&&"="!==(r=e.charAt(o))&&";"!==r&&","!==r;)o+=1;o<e.length&&"="===e.charAt(o)?(s=!0,o=n,a.push(e.substring(t,i)),t=o):o=i+1}else o+=1;(!s||o>=e.length)&&a.push(e.substring(t,e.length))}return a}(n)){let t=l(e);t&&this._parsed.set(t.name,t)}}get(...e){let t="string"==typeof e[0]?e[0]:e[0].name;return this._parsed.get(t)}getAll(...e){var t;let r=Array.from(this._parsed.values());if(!e.length)return r;let i="string"==typeof e[0]?e[0]:null==(t=e[0])?void 0:t.name;return r.filter(e=>e.name===i)}has(e){return this._parsed.has(e)}set(...e){let[t,r,i]=1===e.length?[e[0].name,e[0].value,e[0]]:e,n=this._parsed;return n.set(t,function(e={name:"",value:""}){return"number"==typeof e.expires&&(e.expires=new Date(e.expires)),e.maxAge&&(e.expires=new Date(Date.now()+1e3*e.maxAge)),(null===e.path||void 0===e.path)&&(e.path="/"),e}({name:t,value:r,...i})),function(e,t){for(let[,r]of(t.delete("set-cookie"),e)){let e=a(r);t.append("set-cookie",e)}}(n,this._headers),this}delete(...e){let[t,r,i]="string"==typeof e[0]?[e[0]]:[e[0].name,e[0].path,e[0].domain];return this.set({name:t,path:r,domain:i,value:"",expires:new Date(0)})}[Symbol.for("edge-runtime.inspect.custom")](){return`ResponseCookies ${JSON.stringify(Object.fromEntries(this._parsed))}`}toString(){return[...this._parsed.values()].map(a).join("; ")}}},"./dist/compiled/cookie/index.js":e=>{(()=>{"use strict";"undefined"!=typeof __nccwpck_require__&&(__nccwpck_require__.ab=__dirname+"/");var t={};(()=>{/*!
+(()=>{var e={"../next-env/dist/index.js":(e,t,r)=>{(()=>{var t={383:e=>{"use strict";e.exports.j=function(e){let t=e.ignoreProcessEnv?{}:process.env;for(let r in e.parsed){let i=Object.prototype.hasOwnProperty.call(t,r)?t[r]:e.parsed[r];e.parsed[r]=(function e(t,r,i){let n=function(e,t){let r=Array.from(e.matchAll(t));return r.length>0?r.slice(-1)[0].index:-1}(t,/(?!(?<=\\))\$/g);if(-1===n)return t;let s=t.slice(n).match(/((?!(?<=\\))\${?([\w]+)(?::-([^}\\]*))?}?)/);if(null!=s){let[,n,a,o]=s;return e(t.replace(n,r[a]||o||i.parsed[a]||""),r,i)}return t})(i,t,e).replace(/\\\$/g,"$")}for(let r in e.parsed)t[r]=e.parsed[r];return e}},234:(e,t,r)=>{let i=r(147),n=r(17),s=r(37),a=r(113),o=r(803).version,l=/(?:^|^)\s*(?:export\s+)?([\w.-]+)(?:\s*=\s*?|:\s+?)(\s*'(?:\\'|[^'])*'|\s*"(?:\\"|[^"])*"|\s*`(?:\\`|[^`])*`|[^#\r\n]+)?\s*(?:#.*)?(?:$|$)/gm;function h(e){console.log(`[dotenv@${o}][DEBUG] ${e}`)}function d(e){return e&&e.DOTENV_KEY&&e.DOTENV_KEY.length>0?e.DOTENV_KEY:process.env.DOTENV_KEY&&process.env.DOTENV_KEY.length>0?process.env.DOTENV_KEY:""}function u(e){let t=n.resolve(process.cwd(),".env");return e&&e.path&&e.path.length>0&&(t=e.path),t.endsWith(".vault")?t:`${t}.vault`}let c={configDotenv:function(e){let t=n.resolve(process.cwd(),".env"),r="utf8",a=!!(e&&e.debug);if(e){if(null!=e.path){var o;t="~"===(o=e.path)[0]?n.join(s.homedir(),o.slice(1)):o}null!=e.encoding&&(r=e.encoding)}try{let n=c.parse(i.readFileSync(t,{encoding:r})),s=process.env;return e&&null!=e.processEnv&&(s=e.processEnv),c.populate(s,n,e),{parsed:n}}catch(e){return a&&h(`Failed to load ${t} ${e.message}`),{error:e}}},_configVault:function(e){console.log(`[dotenv@${o}][INFO] Loading env from encrypted .env.vault`);let t=c._parseVault(e),r=process.env;return e&&null!=e.processEnv&&(r=e.processEnv),c.populate(r,t,e),{parsed:t}},_parseVault:function(e){let t;let r=u(e),i=c.configDotenv({path:r});if(!i.parsed)throw Error(`MISSING_DATA: Cannot parse ${r} for an unknown reason`);let n=d(e).split(","),s=n.length;for(let e=0;e<s;e++)try{let r=n[e].trim(),s=function(e,t){let r;try{r=new URL(t)}catch(e){if("ERR_INVALID_URL"===e.code)throw Error("INVALID_DOTENV_KEY: Wrong format. Must be in valid uri format like dotenv://:key_1234@dotenv.org/vault/.env.vault?environment=development");throw e}let i=r.password;if(!i)throw Error("INVALID_DOTENV_KEY: Missing key part");let n=r.searchParams.get("environment");if(!n)throw Error("INVALID_DOTENV_KEY: Missing environment part");let s=`DOTENV_VAULT_${n.toUpperCase()}`,a=e.parsed[s];if(!a)throw Error(`NOT_FOUND_DOTENV_ENVIRONMENT: Cannot locate environment ${s} in your .env.vault file.`);return{ciphertext:a,key:i}}(i,r);t=c.decrypt(s.ciphertext,s.key);break}catch(t){if(e+1>=s)throw t}return c.parse(t)},config:function(e){let t=u(e);if(0===d(e).length)return c.configDotenv(e);if(!i.existsSync(t)){var r;return r=`You set DOTENV_KEY but you are missing a .env.vault file at ${t}. Did you forget to build it?`,console.log(`[dotenv@${o}][WARN] ${r}`),c.configDotenv(e)}return c._configVault(e)},decrypt:function(e,t){let r=Buffer.from(t.slice(-64),"hex"),i=Buffer.from(e,"base64"),n=i.slice(0,12),s=i.slice(-16);i=i.slice(12,-16);try{let e=a.createDecipheriv("aes-256-gcm",r,n);return e.setAuthTag(s),`${e.update(i)}${e.final()}`}catch(i){let e=i instanceof RangeError,t="Invalid key length"===i.message,r="Unsupported state or unable to authenticate data"===i.message;if(e||t)throw Error("INVALID_DOTENV_KEY: It must be 64 characters long (or more)");if(r)throw Error("DECRYPTION_FAILED: Please check your DOTENV_KEY");throw console.error("Error: ",i.code),console.error("Error: ",i.message),i}},parse:function(e){let t;let r={},i=e.toString();for(i=i.replace(/\r\n?/gm,"\n");null!=(t=l.exec(i));){let e=t[1],i=t[2]||"",n=(i=i.trim())[0];i=i.replace(/^(['"`])([\s\S]*)\1$/gm,"$2"),'"'===n&&(i=(i=i.replace(/\\n/g,"\n")).replace(/\\r/g,"\r")),r[e]=i}return r},populate:function(e,t,r={}){let i=!!(r&&r.debug),n=!!(r&&r.override);if("object"!=typeof t)throw Error("OBJECT_REQUIRED: Please check the processEnv argument being passed to populate");for(let r of Object.keys(t))Object.prototype.hasOwnProperty.call(e,r)?(!0===n&&(e[r]=t[r]),i&&(!0===n?h(`"${r}" is already defined and WAS overwritten`):h(`"${r}" is already defined and was NOT overwritten`))):e[r]=t[r]}};e.exports.configDotenv=c.configDotenv,e.exports._configVault=c._configVault,e.exports._parseVault=c._parseVault,e.exports.config=c.config,e.exports.decrypt=c.decrypt,e.exports.parse=c.parse,e.exports.populate=c.populate,e.exports=c},113:e=>{"use strict";e.exports=r("crypto")},147:e=>{"use strict";e.exports=r("fs")},37:e=>{"use strict";e.exports=r("os")},17:e=>{"use strict";e.exports=r("path")},803:e=>{"use strict";e.exports=JSON.parse('{"name":"dotenv","version":"16.3.1","description":"Loads environment variables from .env file","main":"lib/main.js","types":"lib/main.d.ts","exports":{".":{"types":"./lib/main.d.ts","require":"./lib/main.js","default":"./lib/main.js"},"./config":"./config.js","./config.js":"./config.js","./lib/env-options":"./lib/env-options.js","./lib/env-options.js":"./lib/env-options.js","./lib/cli-options":"./lib/cli-options.js","./lib/cli-options.js":"./lib/cli-options.js","./package.json":"./package.json"},"scripts":{"dts-check":"tsc --project tests/types/tsconfig.json","lint":"standard","lint-readme":"standard-markdown","pretest":"npm run lint && npm run dts-check","test":"tap tests/*.js --100 -Rspec","prerelease":"npm test","release":"standard-version"},"repository":{"type":"git","url":"git://github.com/motdotla/dotenv.git"},"funding":"https://github.com/motdotla/dotenv?sponsor=1","keywords":["dotenv","env",".env","environment","variables","config","settings"],"readmeFilename":"README.md","license":"BSD-2-Clause","devDependencies":{"@definitelytyped/dtslint":"^0.0.133","@types/node":"^18.11.3","decache":"^4.6.1","sinon":"^14.0.1","standard":"^17.0.0","standard-markdown":"^7.1.0","standard-version":"^9.5.0","tap":"^16.3.0","tar":"^6.1.11","typescript":"^4.8.4"},"engines":{"node":">=12"},"browser":{"fs":false}}')}},i={};function n(e){var r=i[e];if(void 0!==r)return r.exports;var s=i[e]={exports:{}},a=!0;try{t[e](s,s.exports,n),a=!1}finally{a&&delete i[e]}return s.exports}n.n=e=>{var t=e&&e.__esModule?()=>e.default:()=>e;return n.d(t,{a:t}),t},n.d=(e,t)=>{for(var r in t)n.o(t,r)&&!n.o(e,r)&&Object.defineProperty(e,r,{enumerable:!0,get:t[r]})},n.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t),n.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},n.ab=__dirname+"/";var s={};(()=>{"use strict";let e,t,r;n.r(s),n.d(s,{initialEnv:()=>e,updateInitialEnv:()=>u,processEnv:()=>p,resetEnv:()=>f,loadEnvConfig:()=>m});var i=n(147);n.n(i);var a=n(17);n.n(a);var o=n(234);n.n(o);var l=n(383);let h=[],d=[];function u(t){Object.assign(e||{},t)}function c(e){Object.keys(process.env).forEach(t=>{t.startsWith("__NEXT_PRIVATE")||void 0!==e[t]&&""!==e[t]||delete process.env[t]}),Object.entries(e).forEach(([e,t])=>{process.env[e]=t})}function p(t,r,i=console,n=!1,s){var h;if(e||(e=Object.assign({},process.env)),!n&&(process.env.__NEXT_PROCESSED_ENV||0===t.length))return[process.env];process.env.__NEXT_PROCESSED_ENV="true";let u=Object.assign({},e),c={};for(let e of t)try{let t={};for(let r of(t.parsed=o.parse(e.contents),(t=(0,l.j)(t)).parsed&&!d.some(t=>t.contents===e.contents&&t.path===e.path)&&(null==s||s(e.path)),Object.keys(t.parsed||{})))void 0===c[r]&&void 0===u[r]&&(c[r]=null===(h=t.parsed)||void 0===h?void 0:h[r])}catch(t){i.error(`Failed to load env from ${a.join(r||"",e.path)}`,t)}return[Object.assign(process.env,c),c]}function f(){e&&c(e)}function m(n,s,o=console,l=!1,u){if(e||(e=Object.assign({},process.env)),t&&!l)return{combinedEnv:t,parsedEnv:r,loadedEnvFiles:h};c(e),d=h,h=[];let f=s?"development":"production";for(let e of[`.env.${f}.local`,"test"!==f&&".env.local",`.env.${f}`,".env"].filter(Boolean)){let t=a.join(n,e);try{if(!i.statSync(t).isFile())continue;let r=i.readFileSync(t,"utf8");h.push({path:e,contents:r})}catch(t){"ENOENT"!==t.code&&o.error(`Failed to load env from ${e}`,t)}}return[t,r]=p(h,n,o,l,u),{combinedEnv:t,parsedEnv:r,loadedEnvFiles:h}}})(),e.exports=s})()},"./dist/compiled/@edge-runtime/cookies/index.js":e=>{"use strict";var t=Object.defineProperty,r=Object.getOwnPropertyDescriptor,i=Object.getOwnPropertyNames,n=Object.prototype.hasOwnProperty,s={};function a(e){var t;let r=["path"in e&&e.path&&`Path=${e.path}`,"expires"in e&&(e.expires||0===e.expires)&&`Expires=${("number"==typeof e.expires?new Date(e.expires):e.expires).toUTCString()}`,"maxAge"in e&&"number"==typeof e.maxAge&&`Max-Age=${e.maxAge}`,"domain"in e&&e.domain&&`Domain=${e.domain}`,"secure"in e&&e.secure&&"Secure","httpOnly"in e&&e.httpOnly&&"HttpOnly","sameSite"in e&&e.sameSite&&`SameSite=${e.sameSite}`,"partitioned"in e&&e.partitioned&&"Partitioned","priority"in e&&e.priority&&`Priority=${e.priority}`].filter(Boolean),i=`${e.name}=${encodeURIComponent(null!=(t=e.value)?t:"")}`;return 0===r.length?i:`${i}; ${r.join("; ")}`}function o(e){let t=new Map;for(let r of e.split(/; */)){if(!r)continue;let e=r.indexOf("=");if(-1===e){t.set(r,"true");continue}let[i,n]=[r.slice(0,e),r.slice(e+1)];try{t.set(i,decodeURIComponent(null!=n?n:"true"))}catch{}}return t}function l(e){var t,r;if(!e)return;let[[i,n],...s]=o(e),{domain:a,expires:l,httponly:u,maxage:c,path:p,samesite:f,secure:m,partitioned:g,priority:v}=Object.fromEntries(s.map(([e,t])=>[e.toLowerCase(),t]));return function(e){let t={};for(let r in e)e[r]&&(t[r]=e[r]);return t}({name:i,value:decodeURIComponent(n),domain:a,...l&&{expires:new Date(l)},...u&&{httpOnly:!0},..."string"==typeof c&&{maxAge:Number(c)},path:p,...f&&{sameSite:h.includes(t=(t=f).toLowerCase())?t:void 0},...m&&{secure:!0},...v&&{priority:d.includes(r=(r=v).toLowerCase())?r:void 0},...g&&{partitioned:!0}})}((e,r)=>{for(var i in r)t(e,i,{get:r[i],enumerable:!0})})(s,{RequestCookies:()=>u,ResponseCookies:()=>c,parseCookie:()=>o,parseSetCookie:()=>l,stringifyCookie:()=>a}),e.exports=((e,s,a,o)=>{if(s&&"object"==typeof s||"function"==typeof s)for(let l of i(s))n.call(e,l)||l===a||t(e,l,{get:()=>s[l],enumerable:!(o=r(s,l))||o.enumerable});return e})(t({},"__esModule",{value:!0}),s);var h=["strict","lax","none"],d=["low","medium","high"],u=class{constructor(e){this._parsed=new Map,this._headers=e;let t=e.get("cookie");if(t)for(let[e,r]of o(t))this._parsed.set(e,{name:e,value:r})}[Symbol.iterator](){return this._parsed[Symbol.iterator]()}get size(){return this._parsed.size}get(...e){let t="string"==typeof e[0]?e[0]:e[0].name;return this._parsed.get(t)}getAll(...e){var t;let r=Array.from(this._parsed);if(!e.length)return r.map(([e,t])=>t);let i="string"==typeof e[0]?e[0]:null==(t=e[0])?void 0:t.name;return r.filter(([e])=>e===i).map(([e,t])=>t)}has(e){return this._parsed.has(e)}set(...e){let[t,r]=1===e.length?[e[0].name,e[0].value]:e,i=this._parsed;return i.set(t,{name:t,value:r}),this._headers.set("cookie",Array.from(i).map(([e,t])=>a(t)).join("; ")),this}delete(e){let t=this._parsed,r=Array.isArray(e)?e.map(e=>t.delete(e)):t.delete(e);return this._headers.set("cookie",Array.from(t).map(([e,t])=>a(t)).join("; ")),r}clear(){return this.delete(Array.from(this._parsed.keys())),this}[Symbol.for("edge-runtime.inspect.custom")](){return`RequestCookies ${JSON.stringify(Object.fromEntries(this._parsed))}`}toString(){return[...this._parsed.values()].map(e=>`${e.name}=${encodeURIComponent(e.value)}`).join("; ")}},c=class{constructor(e){var t,r,i;this._parsed=new Map,this._headers=e;let n=null!=(i=null!=(r=null==(t=e.getSetCookie)?void 0:t.call(e))?r:e.get("set-cookie"))?i:[];for(let e of Array.isArray(n)?n:function(e){if(!e)return[];var t,r,i,n,s,a=[],o=0;function l(){for(;o<e.length&&/\s/.test(e.charAt(o));)o+=1;return o<e.length}for(;o<e.length;){for(t=o,s=!1;l();)if(","===(r=e.charAt(o))){for(i=o,o+=1,l(),n=o;o<e.length&&"="!==(r=e.charAt(o))&&";"!==r&&","!==r;)o+=1;o<e.length&&"="===e.charAt(o)?(s=!0,o=n,a.push(e.substring(t,i)),t=o):o=i+1}else o+=1;(!s||o>=e.length)&&a.push(e.substring(t,e.length))}return a}(n)){let t=l(e);t&&this._parsed.set(t.name,t)}}get(...e){let t="string"==typeof e[0]?e[0]:e[0].name;return this._parsed.get(t)}getAll(...e){var t;let r=Array.from(this._parsed.values());if(!e.length)return r;let i="string"==typeof e[0]?e[0]:null==(t=e[0])?void 0:t.name;return r.filter(e=>e.name===i)}has(e){return this._parsed.has(e)}set(...e){let[t,r,i]=1===e.length?[e[0].name,e[0].value,e[0]]:e,n=this._parsed;return n.set(t,function(e={name:"",value:""}){return"number"==typeof e.expires&&(e.expires=new Date(e.expires)),e.maxAge&&(e.expires=new Date(Date.now()+1e3*e.maxAge)),(null===e.path||void 0===e.path)&&(e.path="/"),e}({name:t,value:r,...i})),function(e,t){for(let[,r]of(t.delete("set-cookie"),e)){let e=a(r);t.append("set-cookie",e)}}(n,this._headers),this}delete(...e){let[t,r,i]="string"==typeof e[0]?[e[0]]:[e[0].name,e[0].path,e[0].domain];return this.set({name:t,path:r,domain:i,value:"",expires:new Date(0)})}[Symbol.for("edge-runtime.inspect.custom")](){return`ResponseCookies ${JSON.stringify(Object.fromEntries(this._parsed))}`}toString(){return[...this._parsed.values()].map(a).join("; ")}}},"./dist/compiled/cookie/index.js":e=>{(()=>{"use strict";"undefined"!=typeof __nccwpck_require__&&(__nccwpck_require__.ab=__dirname+"/");var t={};(()=>{/*!
* cookie
* Copyright(c) 2012-2014 Roman Shtylman
* Copyright(c) 2015 Douglas Christopher Wilson
As we now also get typed env variables, will we also get typed page & layout params? (Kind of like NextPage type of the pages directory, but the params attribute is generated based on the path params) |
@@ -257,6 +260,11 @@ export async function startServer( | |||
const startServerInfo = await getStartServerInfo(dir, isDev) | |||
envInfo = startServerInfo.envInfo | |||
expFeatureInfo = startServerInfo.expFeatureInfo | |||
|
|||
// opt out if typedEnv is set to false | |||
if (startServerInfo.nextConfig.typedEnv !== false) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this will be duplicated, it will executed on setup-dev-bundler in dev. We don't need it here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
setup-dev-bundler
runs on envChange
for HMR, should I add some logic there to run initially?
x-ref: here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the one in setup-dev is going to run anyway for initial start, we don't need to call it here.
If your purpose is to do type check in build mode, then might need to parse the env file and write before build TS check started.
/** @type {import('next').NextConfig} */ | ||
const nextConfig = { | ||
// enabled by default, opt out by setting to false | ||
typedEnv: false, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's give this at least a non-abbreviated name for readability. It's only typed once so the name can be even more descriptive.
packages/next/src/cli/next-dev.ts
Outdated
@@ -202,12 +202,15 @@ const nextDev = async ( | |||
traceUploadUrl = options.experimentalUploadTrace | |||
} | |||
|
|||
const distDir = path.join(dir, config.distDir ?? '.next') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
aside: Shouldn't this have gotten the default value closer to where we initialize config
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Um I didn't add it but just moved above the original resolving!
@@ -257,6 +260,11 @@ export async function startServer( | |||
const startServerInfo = await getStartServerInfo(dir, isDev) | |||
envInfo = startServerInfo.envInfo | |||
expFeatureInfo = startServerInfo.expFeatureInfo | |||
|
|||
// opt out if typedEnv is set to false | |||
if (startServerInfo.nextConfig.typedEnv !== false) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the one in setup-dev is going to run anyway for initial start, we don't need to call it here.
If your purpose is to do type check in build mode, then might need to parse the env file and write before build TS check started.
It's not clear to me what's type checked now, that wasn't before.
But the code is shipped to production as well. Why wouldn't we not want to offer autocomplete in those cases? |
Type-checking allows autocompletion, and validate the env was loaded (no need assumption like Updated the description as well.
It is because the Dev Server does not load the production-specific env files (e.g. |
I think we should rename it to type hint for development. Since the PR is not covering production build checking atm, where it could bail the build when types are not matched. Could do it in the following PR. |
// we ensure the types directory exists on turbo | ||
if (usingTypeScript && opts.turbo) { | ||
const distTypesDir = path.join(distDir, 'types') | ||
if (!fs.existsSync(distTypesDir)) { | ||
await mkdir(distTypesDir, { recursive: true }) | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@huozhi Since turbo don't generate types
dir like our webpack plugin does, we ensure it is generated here for further typed...
features.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Empty env.d.ts
don't affect existing envs:
Screen.Recording.2024-07-10.at.5.40.09.PM.mov
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we check if types dir is created in the type creation util so we don't have to do that logic for turbopack specifically? This might be easily forgotten to update later on
packages/next/src/server/lib/experimental/create-env-definitions.ts
Outdated
Show resolved
Hide resolved
// we ensure the types directory exists on turbo | ||
if (usingTypeScript && opts.turbo) { | ||
const distTypesDir = path.join(distDir, 'types') | ||
if (!fs.existsSync(distTypesDir)) { | ||
await mkdir(distTypesDir, { recursive: true }) | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we check if types dir is created in the type creation util so we don't have to do that logic for turbopack specifically? This might be easily forgotten to update later on
For prod build it's a bit more complicated. One environment variable might not be existing during build time, but only provided when running the application ( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good work, let's ship it and handle the deleting envs case in the following up PRs
@@ -149,6 +151,14 @@ async function startWatcher(opts: SetupOpts) { | |||
|
|||
const distDir = path.join(opts.dir, opts.nextConfig.distDir) | |||
|
|||
// we ensure the types directory exists here |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This comment is not necessary here since we're ensuring the directory anyway
// we ensure the types directory exists here |
That's not what people generally understand under type-checking. We don't check if the specified variable actually exists.
For some reason, in Next.js, you already got a non-nullable string for arbitrary members of |
Since const foo = (str: string) => str
foo(process.env.FOO)
^^^^^^^^^^^^^^^
// Argument of type 'string | undefined' is not assignable to parameter of type 'string'.
// Type 'undefined' is not assignable to type 'string'.ts(2345)
foo(process.env.FOO as string)
foo(process.env.FOO!) I think the word |
ProcessEnv type should be |
Why?
Users can benefit the autocomplete and type-checking environment variable experience.
Autocompletion
As we have multiple entries for loading the env (e.g., env.local, .env, etc.), the user has to check each time if the proper environment exists and type its full name.
Type-checking
The default type of
process.env['key']
from @types/node isstring | undefined
.This adds extra steps when accessing
env
, which requires a string value.The extra steps could include type alias, or explicitly setting as not-null.
What?
This PR added
experimental.typedEnv
that generates a.d.ts
file on Dev Server.It generates from the loaded env files, except production specific files like
.env.production.local
.It is because the Dev Server does not load the production-specific env files.
How?
When starting the dev server, we read off the env files and next config.
If we validate that there is
experimental.typedEnv
set as true in next config, we generate aenv.d.ts
file inside thedistDir
(.next
by default).If there is a change in the env files, we rewrite the
env.d.ts
file.Closes NEXT-542