Як імпортувати файл JSON у файл TypeScript?


86

Я створюю додаток карти за допомогою Angular Maps і хочу імпортувати файл JSON як список маркерів, що визначають місця розташування. Я сподіваюся використовувати цей файл JSON як масив marker [] всередині app.component.ts. Замість визначення жорстко закодованого масиву маркерів усередині файлу TypeScript.

Який найкращий процес імпорту цього JSON-файлу для використання в моєму проекті? Будь-який напрямок дуже вдячний!


Ви можете побачити мою відповідь, оскільки вона застосовується до Angular 7+
Юліан

Відповіді:


115

Однокласний лайнер Aonepathan працював у мене до останнього оновлення машинопису.

Я знайшов Jecelyn Yeen в пост , який пропонує розміщення цього фрагмента коду в файл Визначення TS

додати файл typings.d.tsдо кореневої папки проекту із вмістом нижче

declare module "*.json" {
    const value: any;
    export default value;
}

а потім імпортуйте дані так:

import * as data from './example.json';

оновлення липня 2019:

Машинопис 2.9 ( docs ) представив краще, розумніше рішення. Кроки:

  1. Додайте resolveJsonModuleпідтримку за допомогою цього рядка у своєму tsconfig.jsonфайлі:
"compilerOptions": {
    ...
    "resolveJsonModule": true
  }

оператор import тепер може передбачати експорт за замовчуванням:

import data from './example.json';

а intellisense тепер перевірить файл json, чи можна використовувати методи Array тощо. дуже здорово.


3
Це спрацювало і на мене - надзвичайно гладко! ПРИМІТКА. Для правильної компіляції потрібно перезапустити сервер розробників.
Скотт Байерс,

13
Я отримуюCannot find module '*.json'. Consider using '--resolveJsonModule' to import module with '.json' extensionts(2732)
Jeremy Thille

4
Мені також потрібно було додати, "esModuleInterop": true,як зазначено в документах машинопису, однак там також кажуть використовувати commonjsяк moduleзамість esnext. Здається, це працює з обома. Чи є підстави переходити на commonjs (як згадується в документах), а не дотримуватися типового esnext?
timhc22

1
так само, як і коментарі вище мені потрібні "esModuleInterop":true. Також код VS все ще показує мені помилку .. але все працює нормально
mikey

6
Я повинен був додати "allowSyntheticDefaultImports": trueв compilerOptionsа з новим кутовим 9.1.11 проекту.
yohosuff

28

Як зазначено в цій публікації на Reddit , після Angular 7 ви можете спростити ці два кроки:

  1. Додайте ці три рядки compilerOptionsу свій tsconfig.jsonфайл:
"resolveJsonModule": true,
"esModuleInterop": true,
"allowSyntheticDefaultImports": true
  1. Імпортуйте свої json-дані:
import myData from '../assets/data/my-data.json';

І це все. Тепер ви можете використовувати myDataу своїх компонентах / послугах.


Для чого esModuleInterop?
Джованніпдс

@giovannipds це для імпорту json за замовчуванням
Вася Зарецький,

25

Ось повна відповідь для Angular 6+ на основі відповіді @ryanrain:

З документа angular -cli , json можна розглядати як активи та отримати доступ із стандартного імпорту без використання запиту ajax.

Припустимо, ви додаєте свої файли json у каталог "your-json-dir":

  1. додати "your-json-dir" у файл angular.json (:

    "assets": [ "src/assets", "src/your-json-dir" ]

  2. створити або відредагувати файл typings.d.ts (у корені проекту) та додати наступний вміст:

    declare module "*.json" { const value: any; export default value; }

    Це дозволить імпортувати модулі ".json" без помилок машинопису.

  3. у вашому файлі контролера / служби / будь-чого іншого, просто імпортуйте файл, використовуючи цей відносний шлях:

    import * as myJson from 'your-json-dir/your-json-file.json';


3
Що робити, якщо у мене немає файлу typings.d.ts?
Крістофер Віндзор,

2
тоді вам доведеться створити його в корені проекту лише із вмістом кроку 2
Бенджамін Кауре

2
Важливе зауваження: Додайте власний файл набору тексту до typeRoots у tsconfig.json "typeRoots": ["node_modules / @ types", "src / typings.d.ts"],
Japo Domingo

22

Дякую за введення, хлопці, мені вдалося знайти виправлення, я додав і визначив json поверх файлу app.component.ts:

var json = require('./[yourFileNameHere].json');

Це в кінцевому підсумку створило маркери і являє собою простий рядок коду.


6
Я error TS2304: Cannot find name 'require'.вирішив, додавши declare var require: any;, як це пояснюється в коментарях прийнятої відповіді на питання stackoverflow.com/questions/43104114/… .
Бен,

4
@Ben, вам потрібно додати тип вузла до вашого tsconfig. тобто "compilerOptions": { ... "types": ["node"] },ось відповідна відповідь для тих, хто цього потребує: stackoverflow.com/a/35961176/1754995
Kody

Привіт @aonepathan, сподіваюся, ти можеш мені допомогти: у мене є бібліотека, яка використовує читання файлу json. var json = require('./[yourFileNameHere]');без розширення. Під час компіляції у мене виникає помилка: Module not found: Error: Can't resolve [yourFileNameHere] in [file name]чи є у вас ідея обійти цю проблему?
Neo1975,

16

Перше рішення - просто змініть розширення вашого .json-файлу на .ts та додайте export defaultна початку файлу приблизно так:

export default {
   property: value;
}

Тоді ви можете просто імпортувати файл без необхідності додавати типи, наприклад:

import data from 'data';

Друге рішення - отримати json через HttpClient.

Введіть HttpClient у ваш компонент приблизно так:

export class AppComponent  {
  constructor(public http: HttpClient) {}
}

а потім скористайтеся цим кодом:

this.http.get('/your.json').subscribe(data => {
  this.results = data;
});

https://angular.io/guide/http

Це рішення має одне явне перевагу перед іншими рішеннями, представленими тут - воно не вимагає від вас перебудови цілої програми, якщо ваш json зміниться (він динамічно завантажується з окремого файлу, тому ви можете змінити лише цей файл).


1
перше рішення - це добре, якщо ваші дані статичні і не змінюватимуться дуже довго; це заощадить вам непотрібні http-запити, але якщо ці дані постійно змінюються, використовуйте друге рішення, надіслане сервером, або навіть розгляньте можливість додавання його до бази даних, якщо набір даних величезний
OzzyTheGiant

10

Я прочитав деякі відповіді, і вони, здається, не працювали для мене. Я використовую Typescript 2.9.2, Angular 6 і намагаюся імпортувати JSON в модульному тесті жасмину. Це те, що зробило для мене фокус.

Додати:

"resolveJsonModule": true,

До tsconfig.json

Імпортувати як:

import * as nameOfJson from 'path/to/file.json';

Зупиніться ng test, почніть спочатку.

Посилання: https://blogs.msdn.microsoft.com/typescript/2018/05/31/announcing-typescript-2-9/#json-imports


1
Це було найкраще рішення для мене. Файл типізації не потрібен, і TS може вирішити імена властивостей для вас.
Стів Хоббс,

7

Для Angular 7+,

1) додати файл "typings.d.ts" до кореневої папки проекту (наприклад, src / typings.d.ts):

declare module "*.json" {
    const value: any;
    export default value;
}

2) імпортувати та отримати доступ до даних JSON:

import * as data from 'path/to/jsonData/example.json';
...
export class ExampleComponent {
    constructor() {
        console.log(data.default);
    }

}

або:

import data from 'path/to/jsonData/example.json';
...
export class ExampleComponent {
    constructor() {
        console.log(data);
    }

}

data.default мене повісив. Дякую за повний приклад!
kevin_fitz

Будьте обережні щодо шляху до вашого json-файлу, оскільки він має відношення до файлу, який ви імпортуєте, наприклад, якщо у вас є служба в src/app/services/папці, а ваш json знаходиться в src/assets/data/папці, вам потрібно вказати це як../../assets/data/your.json
Адам Бочек

Це чудово працює, але навіщо потрібен файл typings.d.ts?
Роберт

5

У angular7 я просто використовував

let routesObject = require('./routes.json');

Мій файл routes.json виглядає так

{

    "routeEmployeeList":    "employee-list",
    "routeEmployeeDetail":      "employee/:id"
}

Ви отримуєте доступ до елементів JSON за допомогою

routesObject.routeEmployeeList

Це воно! ;-) Усі інші варіанти такі хакі! Якщо у вас TSLint видасть reuqireпомилку - просто додайте declare var require: any;поверх компонента класу.
Педро Феррейра,

5

Що стосується Typescript 2.9 , можна просто додати:

"compilerOptions": {
    "resolveJsonModule": true
}

до tsconfig.json. Після цього використовувати файл json легко ( і у VSCode також буде приємний висновок типу):

data.json:

{
    "cases": [
        {
            "foo": "bar"
        }
    ]
}

У вашому файлі Typescript:

import { cases } from './data.json';


2
let fs = require('fs');
let markers;
fs.readFile('./markers.json', handleJSONFile);

var handleJSONFile = function (err, data) {
   if (err) {
      throw err;
   }
   markers= JSON.parse(data);
 }

2

Кутова 10

Тепер замість цього слід відредагувати файл tsconfig.app.json(зверніть увагу на "додаток" у назві).

Там ви знайдете compilerOptionsі просто додасте resolveJsonModule: true.

Так, наприклад, файл у абсолютно новому проекті повинен виглядати так:

/* To learn more about this file see: https://angular.io/config/tsconfig. */
{
  "extends": "./tsconfig.base.json",
  "compilerOptions": {
    "outDir": "./out-tsc/app",
    "types": [],
    "resolveJsonModule": true
  },
  "files": [
    "src/main.ts",
    "src/polyfills.ts"
  ],
  "include": [
    "src/**/*.d.ts"
  ]
}
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.