### Install Full Minecraft Client Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs the complete vanilla Minecraft client, including its associated assets and libraries. It requires a `MinecraftLocation` and a `MinecraftVersion` object, typically obtained by fetching the version list. The function returns a Promise that resolves when the installation is complete. ```ts import { getVersionList, MinecraftVersion, install } from "@xmcl/installer"; import { MinecraftLocation } from "@xmcl/core"; const minecraft: MinecraftLocation; const list: MinecraftVersion[] = (await getVersionList()).versions; const aVersion: MinecraftVersion = list[0]; // i just pick the first version in list here await install(aVersion, minecraft); ``` -------------------------------- ### Install Forge from Version List Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Fetches the Forge version list and installs the first available version for a given Minecraft location. This process requires the `getForgeVersionList` and `installForge` functions from the `@xmcl/installer` package. ```ts import { installForge, getForgeVersionList, ForgeVersionList, ForgeVersion } from "@xmcl/installer"; import { MinecraftLocation } from "@xmcl/core"; const list: ForgeVersionList = await getForgeVersionList(); const minecraftLocation: MinecraftLocation; const mcversion = page.mcversion; // mc version const firstVersionOnPage: ForgeVersion = page.versions[0]; await installForge(firstVersionOnPage, minecraftLocation); ``` -------------------------------- ### Install Project Dependencies Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/CONTRIBUTE.md Install all necessary project dependencies using pnpm after cloning the repository and enabling corepack. ```sh pnpm install ``` -------------------------------- ### Monitor Installation Task Progress with Callbacks Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Demonstrates how to use the `installTask` function and its `startAndWait` method to monitor the progress and status of installation tasks. It utilizes callbacks like `onStart`, `onUpdate`, `onFailed`, and `onSucceed` to update the UI and handle task lifecycle events. ```ts declare function updateTaskProgress(task: Task, progress: number, total: number): void; declare function setTaskToFail(task: Task): void; declare function setTaskToSuccess(task: Task): void; declare function trackTask(task: Task): void; const installAllTask: Task = installTask(versionMetadata, mcLocation); await installAllTask.startAndWait({ onStart(task: Task) { // a task start // task.path show the path // task.name is the name trackTask(task) }, onUpdate(task: Task, chunkSize: number) { // a task update // the chunk size usually the buffer size // you can use this to track download speed // you can track this specific task progress updateTaskProgress(task, task.progress, task.total); // or you can update the root task by updateTaskProgress(task, installAllTask.progress, installAllTask.total); }, onFailed(task: Task, error: any) { // on a task fail setTaskToFail(task); }, onSucceed(task: Task, result: any) { // on task success setTaskToSuccess(task); }, // on task is paused/resumed/cancelled onPaused(task: Task) { }, onResumed(task: Task) { }, onCancelled(task: Task) { }, }); ``` -------------------------------- ### Install Minecraft Dependencies Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Ensures that all necessary assets and libraries for a given Minecraft version are installed. It takes a `ResolvedVersion` object, which is parsed from the Minecraft location and version string. This is a convenient way to guarantee a complete installation. ```ts import { installDependencies } from "@xmcl/installer"; import { MinecraftLocation, ResolvedVersion, Version } from "@xmcl/core"; const minecraft: MinecraftLocation; const version: string; // version string like 1.13 const resolvedVersion: ResolvedVersion = await Version.parse(minecraft, version); await installDependencies(resolvedVersion); ``` -------------------------------- ### Install Java 8 from Mojang Source Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs Java 8 by scanning disk paths for Mojang-provided sources. This process requires an LZMA unpacker utility, such as `7zip-bin` or `lzma-native`. The `installJreFromMojang` function from `@xmcl/installer` is utilized. ```ts import { installJreFromMojang } from "@xmcl/installer"; // this require a unpackLZMA util to work // you can use `7zip-bin` // or `lzma-native` for this const unpackLZMA: (src: string, dest: string) => Promise; await installJreFromMojang({ destination: "your/java/home", unpackLZMA, }); ``` -------------------------------- ### Basic Discord RPC Client Initialization Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/discord-rpc/README.md Demonstrates how to initialize the Discord RPC client, set up a 'ready' event listener, and update the user's activity status. This example requires a valid Discord Client ID. ```typescript import { Client } from "@xhayper/discord-rpc"; const client = new Client({ clientId: "123456789012345678" }); client.on("ready", () => { client.user?.setActivity({ state: "Hello, world!" }); }); client.login(); ``` -------------------------------- ### Install nat-api Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/nat-api/README.md Installs the nat-api package using npm. Requires NodeJS version 16 or higher. ```sh npm install @xmcl/nat-api ``` -------------------------------- ### Allocate ByteBuffer Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/bytebuffer/README.md Demonstrates the basic allocation of a ByteBuffer instance, similar to Java's ByteBuffer. This is the common starting point for using the module. ```ts import { ByteBuffer } from '@xmcl/bytebuffer' const bb = ByteBuffer.allocate(10) ``` -------------------------------- ### Install Fabric Client Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs a specific Fabric artifact version to the Minecraft client. Note that this installation does not automatically include Minecraft libraries. The `installFabric` function from `@xmcl/installer` is used. ```ts const minecraftLocation: MinecraftLocation; await installFabric(versionList[0], minecraftLocation); ``` -------------------------------- ### Fetch Fabric Version List Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Retrieves a list of available Fabric artifact versions. This is a prerequisite for installing Fabric. It uses the `getFabricArtifactList` function from the `@xmcl/installer` package. ```ts import { installFabric, FabricArtifactVersion } from "@xmcl/installer"; const versionList: FabricArtifactVersion[] = await getFabricArtifactList(); ``` -------------------------------- ### Install Minecraft Libraries Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs only the required libraries for a specific Minecraft version. It takes a `ResolvedVersion` object, which needs to be parsed from a `MinecraftLocation` and version string. This function is useful for updating or ensuring library integrity. ```ts import { installLibraries } from "@xmcl/installer"; import { ResolvedVersion, MinecraftLocation, Version } from "@xmcl/core"; const minecraft: MinecraftLocation; const version: string; // version string like 1.13 const resolvedVersion: ResolvedVersion = await Version.parse(minecraft, version); await installLibraries(resolvedVersion); ``` -------------------------------- ### Install Forge with Specific Version Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs a specific Forge version along with its associated Minecraft version. This method is useful when the exact Forge version is known. It requires the `installForge` function from `@xmcl/installer`. ```ts import { installForge } from "@xmcl/installer"; const forgeVersion = 'a-forge-version'; // like 31.1.27 await installForge({ version: forgeVersion, mcversion: '1.15.2' }, minecraftLocation); ``` -------------------------------- ### Get Project Details and Version Files from Modrinth API Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/modrinth/README.md Shows how to fetch detailed information for a specific Modrinth project using its ID. It also illustrates how to retrieve version details and access file download URLs and metadata for the project's files. ```ts import { ModrinthV2Client, ProjectVersionFile, ModVersion } from '@xmcl/modrinth' async function getModrinthProjectDetails(projectId: string) { const client = new ModrinthV2Client() const project = await client.getProject(projectId) // project details const versions: string[] = project.versions; if (versions.length > 0) { const oneVersion: string = versions[0]; const modVersion: ModVersion = await client.getProjectVersion(oneVersion); const files: ProjectVersionFile[] = modVersion.files; if (files.length > 0) { const { url, name, hashes } = files[0]; // now you can get file name, file hashes and download url of the file console.log(`First file: Name=${name}, URL=${url}, Hashes=${JSON.stringify(hashes)}`); } } } ``` -------------------------------- ### Limit Installation Concurrency with Undici Dispatcher Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Allows limiting the number of concurrent HTTP connections during installation by providing a custom `undici` Dispatcher. This is useful for managing server load or network resources. The `agent` option accepts a `Dispatcher` configuration. ```ts import { Dispatcher, Agent } from "undici"; const agent = new Agent({ connection: 16 // only 16 connection (socket) we should create at most // you can have other control here. }); await installAssets(resolvedVersion, { agent: { // notice this is the DownloadAgent from `@xmcl/file-transfer` dispatcher: agent // this is the undici Dispatcher option } }); ``` -------------------------------- ### Enable Corepack for pnpm Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/CONTRIBUTE.md Enable Corepack, a tool for managing Node.js package manager versions, to install and use pnpm. ```sh corepack enable ``` -------------------------------- ### Install Minecraft Assets Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Installs only the assets required for a specific Minecraft version. It requires a `ResolvedVersion` object, which is obtained by parsing the Minecraft location and version string. This function is useful for ensuring all game assets are present. ```ts import { installAssets } from "@xmcl/installer"; import { MinecraftLocation, ResolvedVersion, Version } from "@xmcl/core"; const minecraft: MinecraftLocation; const version: string; // version string like 1.13 const resolvedVersion: ResolvedVersion = await Version.parse(minecraft, version); await installAssets(resolvedVersion); ``` -------------------------------- ### Custom Task Identification and Tracking Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Provides an alternative method for tracking tasks by using custom identifiers, such as UUIDs, and user-friendly task names. This approach allows for more flexible integration with UI elements and custom tracking logic. ```ts // you customize function to make task to a user reacable string to display in UI declare function getTaskName(task: Task): string; function runTask(rootTask: Task) { // your own id for this root task const uid = uuid(); await rootTask.startAndWait({ onStart(task: Task) { // tell ui that a task with such name started // the task id is a number id from 0 trackTask(`${uid}.${task.id}`, getTaskName(task)); }, onUpdate(task: Task, chunkSize: number) { // update the total progress updateTaskProgress(`${uid}.${task.id}`, installAllTask.progress, installAllTask.total); }, onStart(task: Task) { // tell ui this task ended endTask(`${uid}.${task.id}`); }, }); } ``` -------------------------------- ### Customize Assets Download Host Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Details how to specify a custom host for downloading game assets using the `assetsHost` option. The host should be configured to serve assets based on their SHA1 hash, with a specific URL structure including a hash prefix. ```ts await installAssets(resolvedVersion, { assetsHost: "https://www.your-url/assets" }); The assets host should accept the get asset request like `GET https://www.your-url/assets//`, where `hash-head` is the first two char in ``. The `` is the sha1 of the asset. ``` -------------------------------- ### Customize Library Download Host Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Explains how to override the default download URLs for libraries using the `libraryHost` option within the `installLibraries` function. This allows users to specify custom or self-hosted locations for library files, with support for multiple fallback URLs. ```ts // the example for call `installLibraries` // this option will also work for other functions involving libraries like `install`, `installDependencies`. await installLibraries(resolvedVersion, { libraryHost(library: ResolvedLibrary) { if (library.name === "commons-io:commons-io:2.5") { // the downloader will first try the first url in the array // if this failed, it will try the 2nd. // if it's still failed, it will try original url return ["https://your-host.org/the/path/to/the/jar", "your-sencodary-url"]; // if you just have one url // just return a string here... } // return undefined if you don't want to change lib url return undefined; }, mavenHost: ['https://www.your-other-maven.org'], // you still can use this to add other maven }); // it will first try you libraryHost url and then try mavenHost url. ``` -------------------------------- ### Task Progress Monitoring and Management Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/task/README.md Demonstrates how to use the `@xmcl/task` module to define custom tasks, manage their execution flow using `yield`, and handle lifecycle events such as start, update, success, failure, pause, resume, and cancellation. This is crucial for tracking operations like downloads in the Minecraft Launcher. ```typescript import { Task, TaskBase, task } from "@xmcl/task"; class ATask extends TaskBase { // implement a task } class BTask extends TaskBase { // implement a task } // suppose you have such task const myTask = task("hello", function() { await this.yield(new ATask().setName("world")); await this.yield(new BTask().setName("xmcl")); }); // start a task const result = await task.startAndWait({ onStart(task: Task) { // the task path is the task name joined by dot (.) const path = task.path; console.log(`${path} started!`); }, onUpdate(task: Task, chunkSize: number) { // a task update }, onFailed(task: Task, error: any) { // on a task fail }, onSucceed(task: Task, result: any) { // on task success const path = task.path; console.log(`${path} ended!`); }, // on task is paused/resumed/cancelled onPaused(task: Task) { }, onResumed(task: Task) { }, onCancelled(task: Task) { }, }); // the result will print like // hello started! // hello.world started! // hello.world ended! // hello.xmcl started! // hello.xmcl ended! // hello ended! ``` -------------------------------- ### Identify Tasks by Path for UI Updates Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/installer/README.md Illustrates how to use the `task.path` property to uniquely identify and update specific tasks within a hierarchical structure in the user interface. The path provides a clear, hierarchical identifier for each operation. ```ts function updateTaskUI(task: Task, progress: number, total: number) { // you can use task.path as identifier // and update the task on UI const path = task.path; // the path can be something like `install.version.json` } ``` -------------------------------- ### Fabric Semantic Version Parsing and Testing Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/semver/README.md Demonstrates how to use the Fabric semantic versioning library to parse version range strings and test if a given version falls within that range. It includes examples for parsing both version ranges and specific versions, highlighting Fabric's extended semver capabilities. ```ts import { parseVersionRange, FabricSemanticVersion } from "@xmcl/semver"; const versionRangeString = ">=1.0+fabric+minecraft"; // this is invalid as a normal semver but valid here const versionRange = parseVersionRange(versionRangeString); const versionString = "1.21"; // a Minecraft version const semver = parseSemanticVersion(versionString); const isVersionInRange = versionRange.test(semver); // is version in this version range ``` -------------------------------- ### Download File with Options Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/file-transfer/README.md Demonstrates downloading a file using the `@xmcl/file-transfer` library, including custom headers, abort signals, progress reporting, and checksum validation. The `download` function takes a configuration object with URL, destination, and optional parameters. ```ts import { download } from '@xmcl/file-transfer' await download({ url: 'http://example.com/file.zip', // required destination: 'file.zip', // required headers: { // optional 'customized': 'header' }, abortSignal: new AbortController().signal, // optional progressController: (url, chunkSize, progress, total) => { // optional console.log(url) console.log(chunkSize) console.log(progress) console.log(total) }, // use validator to validate the file validator: { // optional algorithm: 'sha1', hash: '1234567890abcdef1234567890abcdef12345678', } }) ``` -------------------------------- ### Clone Project Repository Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/CONTRIBUTE.md Clone the project repository from GitHub using Git. This is the first step to setting up your development workspace. ```sh git clone https://github.com/Voxelum/minecraft-launcher-core-node ``` -------------------------------- ### Unified File System Access with openFileSystem Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/system/README.md Demonstrates how to use the `openFileSystem` function from `@xmcl/system` to access files within directories or zip archives. This function abstracts away the underlying file system type, providing a consistent API for reading content. ```TypeScript import { openFileSystem } from "@xmcl/system"; // Example for a directory let filePath = "/path/to/dir/"; const fsDir = await openFileSystem(filePath); console.log(await fsDir.readFile("a.txt")); // Reads /path/to/dir/a.txt // Example for a zip file let zipPath = "/path/to/file.zip"; const fsZip = await openFileSystem(zipPath); console.log(await fsZip.readFile("a.txt")); // Reads a.txt inside the zip file ``` -------------------------------- ### Search Projects in Modrinth API Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/modrinth/README.md Demonstrates how to search for projects on Modrinth using keywords. It utilizes the `ModrinthV2Client` to perform searches and iterates through the results to display project information like ID, title, and description. ```ts import { ModrinthV2Client, SearchOptions, SearchResult } from '@xmcl/modrinth' async function searchModrinthProjects() { const client = new ModrinthV2Client() const searchOptions: SearchOptions = { query: "shader", // searching shader }; const result: SearchResult = await client.searchProjects(searchOptions); const totalProjectCounts = result.total_hits; console.log(`Found ${totalProjectCounts} projects.`); for (const project of result.hits) { console.log(`${project.project_id} ${project.title} ${project.description}`); // print project info } } ``` -------------------------------- ### Build Project Artifacts Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/CONTRIBUTE.md Build the project's output files for different module formats (cjs, esm) and TypeScript declaration files. The --parallel flag optimizes build times. ```sh pnpm build:cjs --parallel # build cjs ``` ```sh pnpm build:esm --parallel # build mjs ``` ```sh pnpm build:type --parallel # build dts ``` -------------------------------- ### Package List for @xmcl/minecraft-launcher-core-node Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/README.md This section lists the available npm packages within the @xmcl/minecraft-launcher-core-node project. Each entry includes the package name, a brief description of its functionality, and its target environment (Node.js or Browser). ```markdown | Package Name | Description | Target Environment | |---|---|---| | @xmcl/game-data | Load level data or servers.dat | Node/Browser | | @xmcl/resourcepack | Parse resource pack | Node/Browser | | @xmcl/task | Util package to create task | Node/Browser | | @xmcl/system | A fs middleware for browser/node | Node/Browser | | @xmcl/semver | The special semver format using by fabricmc. | Node/Browser | | @xmcl/unzip | yauzl unzip wrapper | Node | | @xmcl/file-transfer | High performance undici file download implementation | Node | | @xmcl/nat-api | Port mapping with UPnP and NAT-PMP | Node | | @xmcl/bytebuffer | The bytebuffer module port from bytebuffer.js | Node/Browser | ``` -------------------------------- ### Create and Use UPnP Client Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/nat-api/README.md Demonstrates creating a UPnP client, mapping ports with specific configurations, unmapping ports, retrieving external IP, and managing the client lifecycle. It shows how to map a port for a specified duration and unmap it. ```javascript const { createUpnpClient } = require('nat-api') const client = await createUpnpClient() // map 25565 to 25565 for 1 min: await client.map({ description: "Mapped by @xmcl/nat-api", protocol: 'tcp', public: 25565, private: 25565, ttl: 60 * 1000, }) // Unmap port public and private port 25565 with TCP by default await client.unmap({ port: 25565 }) // Get external IP const mappings = await client.getMappings() // see existed mappings console.log(mappings) // Destroy client client.destroy() ``` -------------------------------- ### Diagnose Minecraft Version Issues Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/core/README.md Gets the report of the version. It can check if version missing assets/libraries. The report contains issues categorized by role, such as 'minecraftJar', 'versionJson', 'library', or 'assets'. ```typescript import { MinecraftLocation, diagnose, ResolvedVersion, MinecraftIssueReport, MinecraftIssues } from "@xmcl/core"; const minecraft: MinecraftLocation; const version: string; // version string like 1.13 const resolvedVersion: ResolvedVersion = await Version.parse(minecraft, version); const report: MinecraftIssueReport = await diagnose(resolvedVersion.id, resolvedVersion.minecraftDirectory); const issues: MinecraftIssues[] = report.issues; for (let issue of issues) { switch (issue.role) { case "minecraftJar": // your jar has problem case "versionJson": // your json has problem case "library": // your lib might be missing or corrupted case "assets": // some assets are missing or corrupted // and so on } } ``` -------------------------------- ### Create Offline User Profile Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/user/README.md Provides examples for creating offline user profiles using the `offline` function from the @xmcl/user library. Users can be created with just a username, or with both a username and a specific UUID. ```typescript import { offline } from "@xmcl/user"; // create a offline user const offlineUser = offline("username"); // create an offline user with uuid const offlineUser1 = offline("username", "uuid"); ``` -------------------------------- ### Launch Minecraft with Server Connection Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/core/README.md Launches Minecraft and connects directly to a server using the `quickPlayMultiplayer` option or the legacy `server` option. Both can be used together for compatibility. ```typescript import { launch, createQuickPlayMultiplayer, ChildProcess } from "@xmcl/core" const gamePath: string; const javaPath: string; const version: string; // Option 1: Use quickPlayMultiplayer directly const proc1 = launch({ gamePath, javaPath, version, quickPlayMultiplayer: 'play.hypixel.net:25565' }); // Option 2: Use helper function const proc2 = launch({ gamePath, javaPath, version, quickPlayMultiplayer: createQuickPlayMultiplayer('mc.example.com', 8080) }); // Legacy server option (still works) const proc3 = launch({ gamePath, javaPath, version, server: { ip: 'play.hypixel.net', port: 25565 } }); // Both options together for compatibility const proc4 = launch({ gamePath, javaPath, version, quickPlayMultiplayer: 'play.hypixel.net:25565', server: { ip: 'play.hypixel.net', port: 25565 } }); ``` -------------------------------- ### Get Curseforge Mod Details by ID Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/curseforge/README.md Explains how to retrieve detailed information for a specific Curseforge mod using its unique ID. It shows how to access properties like mod ID, name, authors, and summary from the returned mod object. ```typescript import { CurseforgeV1Client } from '@xmcl/curseforge' const api = new CurseforgeV1Client(process.env.CURSEFORGE_API_KEY) const mod = await api.getMod(123) console.log(mod.id) // 123 console.log(mod.name) // The mod name console.log(mod.authors) // [{ id: 123, name: 'The author name' }] console.log(mod.summary) // The mod summary ``` -------------------------------- ### Run Tests Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/CONTRIBUTE.md Execute the project's test suite using Vitest. This command runs all tests, and can be used in watch mode for development. ```sh pnpm run test ``` ```sh pnpm vitest ``` -------------------------------- ### Modrinth API Specification Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/modrinth/README.md This entry outlines the core functionalities and endpoints of the Modrinth API as described in their official specification. It covers project searching, retrieval of project details, and version information. ```APIDOC Modrinth API Specification: Base URL: https://api.modrinth.com/v2 Endpoints: 1. **Search Projects** * **Endpoint**: `/api/v2/search * **Method**: GET * **Description**: Searches for projects based on various criteria. * **Query Parameters**: * `query` (string, optional): The search query string. * `limit` (integer, optional): Maximum number of results to return (default: 10, max: 50). * `offset` (integer, optional): Number of results to skip (default: 0). * `facets` (string, optional): JSON string representing search facets (e.g., `[{"project_type": "mod"}]`). * `filter` (string, optional): JSON string representing filters (e.g., `{"versions": "1.19.2"}`). * `sort` (string, optional): Sorting order (e.g., `downloads`, `follows`, `relevance`). * `search_direct` (boolean, optional): If true, only return results that exactly match the query. * **Returns**: `SearchResult` object containing `total_hits` and an array of `Project` objects. 2. **Get Project** * **Endpoint**: `/api/v2/project/{projectId} * **Method**: GET * **Description**: Retrieves detailed information for a specific project. * **Path Parameters**: * `projectId` (string, required): The unique identifier of the project. * **Returns**: `Project` object with comprehensive details. 3. **Get Project Version** * **Endpoint**: `/api/v2/version/{versionId} * **Method**: GET * **Description**: Retrieves details for a specific project version. * **Path Parameters**: * `versionId` (string, required): The unique identifier of the project version. * **Returns**: `ModVersion` object containing version-specific information, including files. 4. **Get Project Versions** * **Endpoint**: `/api/v2/project/{projectId}/version * **Method**: GET * **Description**: Retrieves all versions for a specific project. * **Path Parameters**: * `projectId` (string, required): The unique identifier of the project. * **Query Parameters**: * `featured` (boolean, optional): If true, only return featured versions. * `direct_only` (boolean, optional): If true, only return versions with direct download links. * **Returns**: Array of `ModVersion` objects. Data Structures: * **Project**: Contains `project_id`, `title`, `description`, `versions` (array of version IDs), etc. * **ModVersion**: Contains `id`, `project_id`, `name`, `files` (array of `ProjectVersionFile`), etc. * **ProjectVersionFile**: Contains `url`, `name`, `hashes` (object with MD5, SHA1, SHA512), `size`, etc. Error Handling: * Standard HTTP status codes (e.g., 404 for not found, 400 for bad request). * Error responses typically include a JSON object with an `error` field describing the issue. ``` -------------------------------- ### Read Resource Pack Content by Location Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/resourcepack/README.md Opens a resource pack and allows fetching specific resources like textures or models using a ResourceLocation. The `get` method retrieves a resource, and its `read` method provides the content as a Uint8Array, while `readMetadata` provides associated metadata. ```ts import { ResourcePack, ResourceLocation } from "@xmcl/resourcepack" const fileFullPath = "path/to/pack/some-pack.zip"; const pack: ResourcePack = await ResourcePack.open(fileFullPath); // this is almost the same with original Minecraft // this get the dirt texture png -> minecraft:textures/block/dirt.png const resLocation: ResourceLocation = ResourceLocation.ofTexturePath("block/dirt"); console.log(resLocation); // minecraft:textures/block/dirt.png const resource: Resource | undefined = await pack.get(resLocation); if (resource) { const binaryContent: Uint8Array = await resource.read(); // this is the metadata for resource, like animated texture metadata. const metadata: PackMeta = await resource.readMetadata(); } ``` -------------------------------- ### Get Curseforge Mod File List Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/curseforge/README.md Illustrates fetching the list of files associated with a specific Curseforge mod. It includes options to filter files by game version and mod loader type, and provides access to pagination information for the file list. ```typescript // sample code for get file list for a mod const api = new CurseforgeV1Client(process.env.CURSEFORGE_API_KEY) const { data: files, pagination } = await api.getModFiles({ modId: 1, // your mod id gameVersion: '1.16.5', // support minecraft 1.16.5, optional modLoaderType: FileModLoaderType.Fabric, // only fabric, optional }) const pageSize = pagination.pageSize const index = pagination.index const total = pagination.total // total count const pages = Math.ceil(total / pageSize) // total pages const firstFile = files[0] ``` -------------------------------- ### Search Curseforge Mods by Keyword Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/curseforge/README.md Demonstrates how to search for Curseforge mods using a keyword and various search options like category and filter. It also shows how to access pagination details such as page size, total results, and total pages. ```typescript import { CurseforgeV1Client, SearchOptions } from '@xmcl/curseforge' const api = new CurseforgeV1Client(process.env.CURSEFORGE_API_KEY) const searchOptions: SearchOptions = { categoryId: 6, // 6 is mod, searchFilter: 'search-keyword', }; const result = await api.searchMods(searchOptions) const pageSize = result.pagination.pageSize const total = result.pagination.total const totalPages = Math.ceil(total / pageSize) const mods: Mod[] = result.data // mod details ``` -------------------------------- ### Consuming Packages with Bundlers Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/README.md Guidance on how to consume packages from this project using modern bundlers like esbuild and Vite. It highlights the project's build process using TypeScript and esbuild, which generates both ESM and CommonJS versions, and how bundlers typically resolve the correct module format via the 'module' field in package.json. ```markdown The whole project use typescript and esbuild to build. It will build both `esm` and `commonjs` version js files. Some modules can be used in browser, and they will have browser version built. Nowaday, the bundler should all support reading the `module` field in package.json and use the esm version. If you are using webpack, you can use the `resolve.mainFields` option to specify which field to use. From my experience, the esbuild and vite works pretty fine with current `package.json`. ``` -------------------------------- ### Download File with Fallback URLs Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/file-transfer/README.md Illustrates downloading a file with fallback URLs by providing an array of URLs to the `download` function. The library will attempt to download from the first URL and fall back to subsequent URLs if the initial download fails. ```ts import { download } from '@xmcl/file-transfer' await download({ // using array to fallback url: ['http://example.com/file.zip', 'http://example.com/fallback.zip'], destination: 'file.zip', }) ``` -------------------------------- ### Ping Minecraft Server Status with @xmcl/client Source: https://github.com/voxelum/minecraft-launcher-core-node/blob/master/packages/client/README.md Fetches the status of a Minecraft server using its host and port. The `queryStatus` function allows specifying protocol versions for compatibility and returns server information like MOTD and ping status. ```ts import { queryStatus, Status, QueryOptions } from '@xmcl/client' const serverInfo = { host: 'your host', port: 25565, // be default }; const options: QueryOptions = { /** * see http://wiki.vg/Protocol_version_numbers */ protocol: 203, }; const rawStatusJson: Status = await queryStatus(serverInfo, options); ```