ERR_OSSL_EVP_UNSUPPORTED
➜ next-e-commerce git:(master) ✗ yarn dev
yarn run v1.22.19
$ next dev
Browserslist: caniuse-lite is outdated. Please run:
npx browserslist@latest --update-db
ready - started server on http://localhost:3000
node:internal/crypto/hash:68
this[kHandle] = new _Hash(algorithm, xofLen);
^
Error: error:0308010C:digital envelope routines::unsupported
at new Hash (node:internal/crypto/hash:68:19)
at Object.createHash (node:crypto:138:10)
at module.exports (/Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/webpack/lib/util/createHash.js:135:53)
at NormalModule._initBuildHash (/Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/webpack/lib/NormalModule.js:417:16)
at handleParseError (/Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/webpack/lib/NormalModule.js:471:10)
at /Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/webpack/lib/NormalModule.js:503:5
at /Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/webpack/lib/NormalModule.js:358:12
at /Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/loader-runner/lib/LoaderRunner.js:373:3
at iterateNormalLoaders (/Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/loader-runner/lib/LoaderRunner.js:214:10)
at Array.<anonymous> (/Users/doorahmie/Documents/doorahmie-dev/next-e-commerce/node_modules/loader-runner/lib/LoaderRunner.js:205:4) {
opensslErrorStack: [ 'error:03000086:digital envelope routines::initialization error' ],
library: 'digital envelope routines',
reason: 'unsupported',
code: 'ERR_OSSL_EVP_UNSUPPORTED'
}
이런 에러가 있었다. 위 프로젝트는 nextjs example github으로 노출된 프로젝트를 clone받아 실행한 모습이다.
캡쳐된 이미지로 보는게 눈이 편하다.
tl;dr 아래와 같이 해결하면 된다.
이것도 안되면 여기에 3000외 현재 사용 가능한 다른 포트 기재해주는것이 방법. (ex -p 3001)
하지만, 이유도 궁금했다.
https://stackoverflow.com/questions/69394632/webpack-build-failing-with-err-ossl-evp-unsupported
https://roytuts.com/how-to-fix-err_ossl_evp_unsupported-in-react-js-application/
(바로 위 링크에 따르면 Node.js 17을 사용하는 app에서 'OpenSSL 3.0에서 더 이상 기본적으로 허용되지 않는 알고리즘이나 키 크기를 사용하려고 시도했을 가능성이 높습니다.' 라고 적혀있다.)
*openssl은 데이터 통신을 위한 ssl프로토콜을 이용할 수 있는 오픈소스 라이브러리
*쉘 파일 수정 없이 위에 명령어에 옵션을 추가해주는 편이 내게는 더 맞아서 이렇게 수정했다.
복수의 AI에게도 물어보았다.
네, 맞습니다. NODE_OPTIONS='--openssl-legacy-provider'를 설정하면 Node.js는 OpenSSL의 legacy provider를 사용하여 해시 함수를 구현합니다. legacy provider는 OpenSSL v2.0에서 사용되는 provider입니다.
legacy provider는 OpenSSL v3.0에서 도입된 새로운 기능을 지원하지 않습니다. 따라서 legacy provider를 사용하면 Node.js와 OpenSSL의 해시 함수 규격이 다를 수 있습니다.
예를 들어, OpenSSL v3.0에서는 SHA-3 해시 함수를 지원합니다. 하지만 legacy provider는 SHA-3 해시 함수를 지원하지 않습니다. 따라서 Node.js에서 NODE_OPTIONS='--openssl-legacy-provider'를 설정하고 SHA-3 해시 함수를 사용하면 OpenSSL v3.0에서 사용하는 SHA-3 해시 함수와 다른 해시 값을 생성할 수 있습니다.
다음은 Node.js와 OpenSSL에서 SHA-3 해시를 생성하는 예입니다.
```javascript
const crypto = require("crypto");
const hash = crypto.createHash("sha3-256");
hash.update("Hello, world!");
const digest = hash.digest();
console.log(digest); // "5d41402abc4b2a76b9719d911017c592"
```
다음은 OpenSSL에서 SHA-3 해시를 생성하는 예입니다.
```c
#include <openssl/evp.h>
int main() {
EVP_MD_CTX *ctx;
unsigned char digest[EVP_MAX_MD_SIZE];
unsigned int len;
ctx = EVP_MD_CTX_create();
EVP_DigestInit_ex(ctx, EVP_sha3_256(), NULL);
EVP_DigestUpdate(ctx, "Hello, world!", strlen("Hello, world!"));
EVP_DigestFinal_ex(ctx, digest, &len);
printf("%s\n", digest); // "2236367012424324604133408967076362608894325150638805849378176319135545266039"
EVP_MD_CTX_destroy(ctx);
return 0;
}
```
두 코드 모두 동일한 해시 값인 "2236367012424324604133408967076362608894325150638805849378176319135545266039"를 생성합니다.
하지만 NODE_OPTIONS='--openssl-legacy-provider'를 설정하고 다음과 같이 코드를 실행하면 다른 해시 값을 생성합니다.
```javascript
const crypto = require("crypto");
const hash = crypto.createHash("sha3-256", {
provider: "legacy",
});
hash.update("Hello, world!");
const digest = hash.digest();
console.log(digest); // "8e081a228f1927f4d5a9744078083727e548191369608461966883075f613561"
```
이 경우 Node.js는 OpenSSL의 legacy provider를 사용하여 SHA-3 해시 함수를 구현합니다. legacy provider는 SHA-3 해시 함수를 지원하지 않으므로 다른 해시 값을 생성합니다.
* SHA는 알다시피 Secure Hash Algorithm 이다.
MD5는 널리 사용되는 해시 함수이지만, 2004년에 설계상의 결함이 발견되었다. (그전에도 있었다고...) 해서 이제는 보안관련 용도로 쓰는것은 권장되지 않는다. SHA-256, 384, 512 등을 사용하는 것이 바람직 하다. 위의 부분에서 개선이 있었고, 이 부분이 Node 17버전에는 상충하게 되어 레거시를 사용하라는 명령어 옵션을 줘야 했던 것이다.
늘 그렇듯 결론은 별게 없음. '내가 굳이 보안상 좋지 않은 레거시 옵션을 쓰려고 하는거다' 라고 숙지하고 로컬에서만 쓴다면 문제가 없다.
마지막으로 Node CLI 옵션들의 링크를 글에 추가한다.