ค้นหาเว็บไซต์

typescript - Angular 6/7 "ผลลัพธ์ของการพึ่งพาคือสมการ"


ฉันกำลังพยายามสร้างไลบรารี Angular 6 และใช้งานมันในแอป Angular 6 ฉันได้ลดมันลงเป็นกรณีทดสอบขั้นต่ำ (อัปเดต: เนื่องจาก Angular 7 ออกมาแล้ว ฉันก็ได้ลองใช้เวอร์ชันนั้นด้วย)

ng new workspace # accept the defaults
ng new product # accept the defaults
cd workspace 
ng generate library widgets 
ng build --prod widgets # leave out "--prod" for Angular 7
cd ../product
ng build

แอปที่ชื่อว่า "workspace" เป็นโฮสต์ของไลบรารีที่ชื่อว่า "widgets" แอปอีกตัวที่ชื่อว่า "product" ยืนอยู่คนเดียว ทุกอย่างจนถึงตอนนี้เรียบร้อยดี

ตอนนี้ลองใช้ไลบรารี "widgets" ในแอป "product" เปิดไฟล์ product/src/app/app.module.ts ซึ่งถูกสร้างโดย CLI เพิ่มสองบรรทัดดังที่แสดงด้านล่าง

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';

import { AppComponent } from './app.component';
import { WidgetsModule } from '../../../workspace/dist/widgets'; //  added

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    WidgetsModule // added
  ],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule { }

หลังจากการเปลี่ยนแปลงนั้น เมื่อฉันรัน ng build จากไดเรกทอรีของโปรเจกต์ ฉันได้รับคำเตือนจาก Webpack

Date: 2018-07-31T13:13:08.001Z
Hash: 8a6f58d2ae959edb3cc8
Time: 8879ms
chunk {main} main.js, main.js.map (main) 15.9 kB [initial] [rendered]
chunk {polyfills} polyfills.js, polyfills.js.map (polyfills) 227 kB [initial] [rendered]
chunk {runtime} runtime.js, runtime.js.map (runtime) 5.22 kB [entry] [rendered]
chunk {styles} styles.js, styles.js.map (styles) 15.6 kB [initial] [rendered]
chunk {vendor} vendor.js, vendor.js.map (vendor) 4.59 MB [initial] [rendered]

WARNING in ../workspace/node_modules/@angular/core/fesm5/core.js
4997:15-36 Critical dependency: the request of a dependency is an expression

WARNING in ../workspace/node_modules/@angular/core/fesm5/core.js
5009:15-102 Critical dependency: the request of a dependency is an expression

“ผลลัพธ์ของการขึ้นต่อกันคือการแสดงออก” หมายความว่าอะไร? ฉันกำลังทำอะไรผิดอยู่?

คำตอบ #1

ฉันเจอคำเตือนเหมือนกันเกี่ยวกับ "ผลลัพธ์ของการพึ่งพาเป็นนิพจน์" อ้างอิงถึง fesm5.js ในโปรเจกต์ Angular 7 ที่สร้างด้วย CLI ใหม่

โครงการนี้โดยเฉพาะมีการอ้างอิงไปยังแพ็กเกจ npm ภายในเครื่องด้วยเส้นทางสัมพัทธ์ที่เริ่มต้นด้วย file://../ ซึ่งดูเหมือนว่าจะเป็นสาเหตุของคำเตือน

หลังจากทำการค้นคว้าบ้าง ฉันพบปัญหาใน Github นี้ซึ่งอธิบายว่าเราสามารถแก้ไขมันในแอปที่สร้างด้วย Angular 6+ CLI ได้อย่างไร

สิ่งที่ได้ผลสำหรับฉันคือการเปิดไฟล์ angular.json ในโฟลเดอร์รากของโปรเจกต์ไคลเอนต์ (ไม่ใช่ของไลบรารีที่ใช้ร่วมกัน) และค้นหาเส้นทางนี้:

projects > (your project name) > architect > build > options

และเพิ่มคีย์:

"preserveSymlinks": true

โดยตัดส่วนที่เหลือของไฟล์ทั้งหมดออก นี่คือส่วนที่เกี่ยวข้อง:

{
  "projects": {
    "MyAwesomeProject": {
      "architect": {
        "build": {
          "options": {
            "preserveSymlinks": true
          }
        }
      }
    }
  }
}

หลังจากเพิ่มสิ่งนี้แล้ว ฉันสามารถใช้ ng build ได้ตามปกติโดยไม่มีคำเตือน หวังว่าสิ่งนี้จะช่วยได้นะ!

คำตอบ #2

ปัญหาหลักไม่ได้อยู่ที่ว่าทำไมคุณถึงได้รับคำเตือนนั้น วิธีที่คุณเข้าถึงไลบรารีนั้นไม่ใช่วิธีที่เหมาะสม มาลองพิจารณาวิธีที่ดีกว่าเล็กน้อย [โดยใช้ Angular 7] พร้อมขั้นตอนตัวอย่างของคุณเอง ซึ่งจะไม่ทำให้เกิดปัญหานั้นตั้งแต่แรก

ขั้นตอนที่ 1: [เหมือนของคุณ]

ng new workspace # accept the defaults
ng new product # accept the defaults
cd workspace 
ng generate library widgets 
ng build --prod widgets # leave out "--prod" for Angular 7
cd ../product
ng build

ขั้นตอนที่ 2: สร้างไฟล์ไลบรารี .tgz

cd ../workspace/dist/widgets/
npm pack
cp widgets-0.0.1.tgz ../../../product/

ขั้นตอนที่ 3: เพิ่มไลบรารี "widgets" ในไฟล์ package.json

เปิดไฟล์ package.json ของโปรเจค product และภายใต้ devDependencies ให้เพิ่มบรรทัดต่อไปนี้:

"widgets": "file:./widgets-0.0.1.tgz",

ขั้นตอนที่ 2 และขั้นตอนที่ 3 จำเป็นหากคุณมีไลบรารีในเครื่องของคุณ มิฉะนั้น หากไลบรารีของคุณถูกบรรจุและเผยแพร่ไปยังที่เก็บ npm คุณไม่จำเป็นต้องใช้คำสำคัญ file: คุณสามารถระบุเวอร์ชันเหมือนกับการขึ้นต่ออื่น ๆ ได้เลย

ขั้นตอนที่ 4: ติดตั้งห้องสมุดที่เพิ่งเพิ่มเข้ามา

รัน npm install ในโปรเจกต์ผลิตภัณฑ์

ขั้นตอนที่ 5: ใช้ห้องสมุด

แก้ไขไฟล์ app.module.ts:

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';

import { AppComponent } from './app.component';
import { WidgetsModule } from 'widgets'; // new line

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    WidgetsModule // new line
  ],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule { }

ขั้นตอนที่ 6: สร้างโปรเจกต์ผลิตภัณฑ์

ตอนนี้ ให้รัน ng build ในโครงการผลิตภัณฑ์ มันจะรันสำเร็จ

คำตอบ #3

ข้อผิดพลาดนี้เกิดขึ้นเมื่อการพึ่งพาของ JS ถูกระบุโดยใช้นิพจน์แทนที่จะเป็นสตริงที่กำหนดไว้ เช่น require('horse' + variable) หรือ require(function() { return 'horse' + variable }) เป็นไปได้ว่าบางสิ่งที่ถูกนำเข้ามาโดย WidgetsModule ของคุณกำลังนำเข้าห้องสมุดที่ใช้รูปแบบการ require แบบนั้น

Webpack ร้องเรียนเกี่ยวกับเรื่องนี้เพราะมันหมายความว่ามันต้องรวมไฟล์ทั้งหมดในโฟลเดอร์ แทนที่จะสามารถวิเคราะห์แบบสถิติเพื่อดูว่าไฟล์ใดควรรวม มันก็ยังคงทำงานได้ แต่ตามการอภิปรายเกี่ยวกับปัญหา Webpack นี้ มันไม่ควรถูกละเลย และการพึ่งพาที่เกี่ยวข้องควรถูกปรับโครงสร้างใหม่

ฉันเจอข้อผิดพลาดนี้ในระหว่างกระบวนการอัปเกรด Angular จากเวอร์ชัน 5 เป็นเวอร์ชัน 6 ในโปรเจ็กต์เมื่อเร็ว ๆ นี้ และถ้าจำไม่ผิด ข้อผิดพลาดก็หายไปหลังจากที่ฉันอัปเกรด dependency อื่น ๆ ทั้งหมดเป็นเวอร์ชันล่าสุดด้วย - แต่ฉันไม่สามารถบอกได้ว่า dependency ตัวไหนที่เป็นสาเหตุของปัญหา และน่าเสียดายที่ฉันไม่ได้ commit ระหว่างที่เห็นข้อผิดพลาดกับการแก้ไข ดังนั้นฉันจึงไม่สามารถวิเคราะห์ได้ว่าการเปลี่ยนแปลงใดที่แก้ไขข้อผิดพลาดได้อย่างชัดเจน

ดูเหมือนว่าหลายคนกำลังประสบปัญหาคล้ายกัน - ดูตัวอย่างเช่น https://github.com/angular/angular/issues/20357

ในการลบคำเตือน (โดยไม่แก้ไขปัญหาที่แท้จริง) คุณจะต้องทำตามกระบวนการนี้ โดยเพิ่ม:

plugins: [
    // Workaround for Critical dependency 
    // The request of a dependency is an expression in ./node_modules/@angular/core/fesm5/core.js
    new webpack.ContextReplacementPlugin(
        /\@angular(\\|\/)core(\\|\/)fesm5/,
        helpers.root('./src'),
        {}
    )
]

... ไปยังการกำหนดค่า webpack อย่างไรก็ตาม ใน Angular CLI เวอร์ชันล่าสุด คุณไม่สามารถแก้ไขการกำหนดค่า webpack ด้วยตนเองได้ (คำสั่ง ng eject เก่าที่เคยอนุญาตให้ทำสิ่งนี้ได้ถูกลบไปแล้ว) ดังนั้นฉันจึงไม่เชื่อว่าคุณสามารถแก้ไขคำเตือนนี้ได้ในตอนนี้

ทั้งหมดนี้สรุปได้ว่าคุณจะต้องการให้ผู้เขียนของ Angular CLI ปิดบังข้อผิดพลาดนี้ผ่านการกำหนดค่า webpack ที่สร้างขึ้นซึ่งใช้ภายใน หรือให้ผู้เขียนของ Angular เปลี่ยนวิธีการที่ core.js ทำการนำเข้า

บทความที่เกี่ยวข้อง