Налаштуйте проект TypeScript із загальними залежностями для створення декількох простих вихідних файлів JavaScript


10

Зараз я пишу кілька сценаріїв для Bot Land . Bot Land - стратегічна гра в реальному часі, де замість того, щоб керувати своїми підрозділами за допомогою миші та клавіатури, ви пишете код, щоб керувати своїми ботами за допомогою API, а потім ваші боти йдуть на боротьбу з іншими ботами. Якщо ви знайомі з підрозділами в SC2, ви можете створити ботів, схожих на моргаючі сталкери, облогові цистерни, медики та ультраліски. (Це досить весела гра для інженерів програмного забезпечення, але це поза сферою цього питання.)

земля бота

Контроль ботів має три рівні зростаючої складності: AI за замовчуванням, мова програмування, схожа на Scratch , та зменшений набір JavaScript під назвою BotLandScript. Хоча вбудований редактор для BotLandScript розумний, ви повинні завантажувати весь код у вигляді одного файлу з глобальними функціями верхнього рівня скрізь. Звичайно, через деякий час це стає болісним, якщо ваш код починає отримувати довгі і різні боти мають однакові функції.

середовище програмування

Щоб полегшити написання коду для декількох ботів, зменшити шанс ненавмисних помилок при кодуванні в голому JS та збільшити шанси на побиття інших гравців, я створив вищевказаний проект TypeScript, щоб забезпечити загальну бібліотеку, а також код для кожного з моїх ботів . Поточна структура каталогу виглядає приблизно так:

lib/ 
  bot.land.d.ts
  common.ts
BlinkStalker/
  BlinkStalker.ts
  tsconfig.json
Artillery/
  Artillery.ts
  tsconfig.json
SmartMelee/
  SmartMelee.ts
  tsconfig.json

libє загальним кодом, який ділиться між ботами, і дає визначення TypeScript для API (не-TS) Bot Land API. Після цього кожен бот отримує власну папку, в якому один файл містить код бота, а інший - панель котлів tsconfig.json:

{
  "compilerOptions": {
    "target": "es3",
    "module": "none",
    "sourceMap": false,
    "outFile": "bot.js"
  },
  "files": [
    "MissileKite.ts"
  ],
  "include": [
    "../lib/**/*"
  ]
}

Коли кожен tsconfig.jsonпобудований, він створює відповідний, bot.jsякий містить перекладений код від самого бота, а також весь код у common.js. Ця настройка є неоптимальною з кількох причин, серед інших: вона вимагає багато дублікатів котла, ускладнює додавання нових ботів, включає багато непотрібного коду для кожного бота і вимагає, щоб кожен бот був побудований окремо.

Однак, базуючись на моєму дослідженні дотепер , не здається, що існує простий спосіб зробити те, що я хочу. Зокрема, використання нової tsc -bопції та посилань не працює, тому що для цього потрібно модулювати модуль, а Bot Land вимагає єдиного файлу з усіма функціями, визначеними на верхньому рівні.

Який найкращий спосіб досягти якомога більшої кількості наступного?

  • Не потрібно нових котлів для додавання нового бота (наприклад, немає tsconfig.jsonна бота)
  • Використовуйте importдля загальних функцій, щоб уникнути виведення невикористаного коду, але потім ...
  • Все-таки виводите всі функції як один єдиний файл у певному форматі Bot Land
  • Один крок збирання, який створює кілька вихідних файлів, по одному для кожного бота
  • Бонус: інтеграція процесу складання з кодом VS. Наразі існує котельна плита tasks.jsonдля створення кожного підпроекту.

Я невпевнено вважаю, що відповідь, ймовірно, передбачає щось на кшталт Грунта tsc, але я не знаю про це, щоб бути впевненим.


Чи потрібно, щоб усі боти мали окремі папки? Або достатньо, щоб кожен бот знаходився на рівні кореня в одному файлі? (наприклад <root>/MissileKite.ts)
a1300

1
Чи повинні бути названі всі перекладені бот-файли bot.js?
a1300

Корінь в одному файлі був би кращим; вони знаходяться в окремих папках через окремі tsconfig.json. Транспільовані ботові файли можуть бути названі будь-якими, бажано, .js версією вихідного файлу. У мене це налаштовано таким чином зараз у репо-репортажі до build/MissileKite.js.
Ендрю Мао

1
@ andrew-mao Ви можете ознайомитись із моїм шаблоном проектів GAS, який відповідає більшості ваших вимог (але орієнтований на інше середовище). Якщо вам це підходить, я можу змогти адаптувати його для вас десь на наступному тижні. github.com/PopGoesTheWza/ts-gas-project-starter
PopGoesTheWza

Є tsconfig-gas.jsonвідповідна річ, яку слід подивитися там?
Ендрю Мао

Відповіді:


2

Ось моя спроба відповісти на ваші вимоги.

Помітні файли:

  • src/tsconfig-botland.jsonмістить налаштування для будь- якого сценарію bot.land (включаючи ваші власні декларації, до яких я перемістився types/bot-land/index.d.ts). Ви можете змінити strictналаштування, які я використовував.
  • src/tsconfig.jsonмістить посилання на всіх ваших ботів. Це файл для редагування, коли ви хочете додати ще один бот-скрипт

Сценарій бота - це щонайменше два файли: мінімалістичний tsconfig.jsonта один чи більше .tsфайлів сценаріїв.

Наприклад src/AggroMiner/tsconfig.json:

{
    "extends": "../tsconfig-botland",
    "compilerOptions": {
        "outFile": "../../build/AggroMiner.js"
    },
    "files": ["index.ts"],
    "include": ["**/*.ts", "../lib/**/*.ts"]
}

У більшості випадків, щоб запустити новий скрипт бота, слід:

  1. скопіюйте будь-яку папку бота (тобто src/AggroMiner) у нову папку підsrc
  2. edit src/<newBotFolder>/tsconfig.jsonдля редагування outFileімені вашого бота
  3. відредагуйте src/tsconfig.jsonта додайте посилання наsrc/<newBotFolder>

Встановлено наступний npm/ yarnсценарій:

  • build створити всіх ботів
  • build-cleanякі очищають buildпапку перед запуском abuild
  • formatзапустити Краще на всіх .tsфайлах підsrc
  • lint запустити перевірку tslint на всіх скриптах бота

Тепер знижуємо свої вимоги:

  • Не потрібно нових котлів для додавання нового бота (наприклад, немає tsconfig.json на бота)

Для цього знадобиться створити якийсь сценарій, який би перерахував папку / сценарії ваших ботів ... та встановив відповідний для бота tsconfig.jsonі запустіть tsc. Якщо це абсолютно не потрібно, мінімальна установка (описати вище) може бути достатньою.

  • Використовуйте імпорт для загальних функцій, щоб уникнути виведення невикористаного коду, але потім ...

По-перше, майте на увазі, що якщо ви почнете використовувати будь-який модуль export/ importоператори, вам знадобиться додаткова третя сторона, щоб упакувати / потискати дерева, щоб досягти єдиного виводу файлу. З того, що я міг зібрати Bot.land, ваші сценарії працюють на сервері. Якщо б мертвий код не вплинув на продуктивність вашого бота, я б не дуже переймався.

  • Все-таки виводите всі функції як один єдиний файл у певному форматі Bot Land

Зроблено.

  • Один крок збирання, який створює кілька вихідних файлів, по одному для кожного бота

Зроблено.

  • Бонус: інтеграція процесу складання з кодом VS. Наразі існує відповідна котла task.json для створення кожного підпроекту.

У npmсценарії повинен з'явитися в списку завдань VSC (принаймні вони роблять в шахті) , таким чином , роблячи tasks.jsonнепотрібним.


Deadcode - прекрасний компроміс для всього іншого, що ви тут зробили; Ви можете мені повідомити, чому ви використовували types/bot-landдля визначення та чому ви вибрали strictналаштування?
Ендрю Мао

Типи / bot-land / index.d.ts насправді є вашим оригінальним .d.ts з lib, перейменованим та розміщеним по-іншому. Припустимо, що це опис загального контексту виконання bot.land для всіх сценаріїв, і, таким чином, я переконуюсь, що він завжди доступний у кожному скрипті бота. "Суворі" налаштування є лише тому, що я ліниво скопіював свої налаштовані налаштування (те ж саме, що і гарніші налаштування). Вони повинні бути адаптовані до переваг користувача (ви).
PopGoesTheWza

Мені просто цікаво, чи є звичайна причина, щоб це вкласти, typesчи це був лише певний спосіб організації, який ви вибрали.
Ендрю Мао

Єдина причина - це припущення, що це контекст bot.land. Подумайте про це як про те, що типи @ type / node вже доступні у ваших сценаріях
nodejs

1
Папка / type - це одне із звичайних місць, де можна ставити декларації зовнішніх типів (тобто специфічний контекст виконання, наприклад, двигун ботландії або нетипізовані модулі / пакети JavaScript, які тут не використовуються)
PopGoesTheWza

3

Ви фактично можете використовувати посилання на проекти. Виконайте ці дії, щоб отримати ті самі результати, які ви отримували для оригінальних файлів, з усіма функціями на верхньому рівні в одному файлі. Однак я не зміг знайти рішення імпортувати лише потрібні функції в боти. Тобто без використання імпорту та експорту.

У вашому tsconfig.json в корені

{
    "files": [],
    "references": [
        { "path": "./lib" }
        { "path": "./AggroMiner" }
        { "path": "./ArtilleryMicro" }
        { "path": "./MissileKite" }
        { "path": "./SmartMelee" }
        { "path": "./ZapKite" }
    ]
}

Далі в папку lib додайте tsconfig.json так

{
  "compilerOptions": {
    "declaration": true,
    "declarationMap": true,
    "composite": true,
    "rootDir": ".",
    "outFile": "../build/lib.js",
    "target": "es3",
    "removeComments": true,
    "sourceMap": false,
  },
  "files": [
    "data.ts",
    "movement.ts",
    "utils.ts"
  ]
}

Нам потрібно внести декілька налаштувань у data.ts, motion.ts та utils.ts, щоб ts не заважав нам помилкам компіляції.

data.ts

/// <reference path="./bot.land.d.ts"/>

(...)

рух.ц


/// <reference path="./data.ts"/>
/// <reference path="./utils.ts"/>
(...)

utils.ts

/// <reference path="./bot.land.d.ts"/>
(...)

Далі ми додаємо base.json в корінь (tsconfig.json ботів розширить його).

base.json

{
  "compilerOptions": {
    "declaration": true,
    "composite": true,
    "rootDir": ".",
    "target": "es3",
    "removeComments": true,
    "sourceMap": false,
  }
}

і tsconfig.json для ботів (адаптувати відповідно до ботів)

{
  "extends": "../base",
  "compilerOptions": {
    "outFile": "../build/AggroMiner.js",
  },
  "files": [
    "AggroMiner.ts"
  ],
  "references": [
      { "path": "../lib", "prepend": true } //note the prepend: true
  ]
}

Це воно. Тепер просто біжи

tsc -b

Тому я подумав про щось подібне, але причина, що це не працює, полягає в тому, що файл, який отримує висновок у вашій гілці, має в своєму розпорядженні купою подібних матеріалів у верхній частині, і для гри потрібен один файл із усіма функціями в ньому. Тоді мені тоді доведеться вручну обклеювати всі складені результати разом, щоб створити файл, який я завантажую, а не просто копіювати вставку файлу. `" використовувати суворо "; експорт .__ esModule = вірно; var data_1 = вимагати ("../ lib / data"); var рух_1 = вимагати ("../ lib / рух"); var utils_1 = requ ("../ lib / utils"); `
Ендрю Мао

Але це працює, оскільки lib також виводиться (вбудовується) у папку збірки (завдяки посиланням).
jperl

Я працював над редагуванням свого коментаря - див. Вище. Або погляньте на те, build/MissileKite.jsщо виводиться під час створення оригінального репо.
Ендрю Мао

@AndrewMao вибачте, лише зараз я розумію, що ви мали на увазі під "тим, що для цього потрібно модулювати модуль і Bot Land вимагає єдиного файлу з усіма функціями, визначеними на верхньому рівні". Я думав про використання "prepend: true", але це вимагає використання outFile і ts не дозволяють нам компілювати файли в lib, оскільки деякі залежать від інших.
jperl

@AndrewMao Я додав підтримку Webpack. Я відредагував публікацію та змістив зміни на репо. Дайте мені знати, якщо це краще.
jperl
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.