A manual fulfillment provider for Medusa e-commerce platform that allows merchants to handle order fulfillments manually
npx @tessl/cli install tessl/npm-medusa-fulfillment-manual@1.1.0Medusa Fulfillment Manual is a minimal fulfillment provider plugin for the Medusa e-commerce platform. It provides a "no-operation" fulfillment service that allows merchants to handle order fulfillments manually through the Medusa admin interface, without integrating with external shipping services.
npm install medusa-fulfillment-manualAs a Medusa plugin, this package is typically not imported directly in application code. Instead, it's registered through the Medusa configuration and accessed via dependency injection:
// The service is available through Medusa's container system
const manualFulfillmentService = container.resolve("manualFulfillmentService");For direct access to the service class (development/testing):
import ManualFulfillmentService from "medusa-fulfillment-manual/src/services/manual-fulfillment";This package is designed to be used as a Medusa plugin. Add it to your medusa-config.js:
const plugins = [
// ... other plugins
"medusa-fulfillment-manual"
];
module.exports = {
projectConfig: {
// ... other config
},
plugins,
};Once configured, the manual fulfillment provider becomes available in the Medusa admin for creating shipping options and handling fulfillments manually.
The package implements the Medusa fulfillment provider interface through a single service class:
FulfillmentService base classThe core service class that provides manual fulfillment capabilities for Medusa stores.
/**
* Manual fulfillment service that extends Medusa's FulfillmentService
* Provides no-operation implementations for all fulfillment operations
*/
class ManualFulfillmentService extends FulfillmentService {
/** Unique identifier for this fulfillment provider */
static identifier: string; // "manual"
constructor();
/** Returns available fulfillment options for orders and returns */
getFulfillmentOptions(): FulfillmentOption[];
/** Validates fulfillment data (pass-through implementation) */
validateFulfillmentData(
optionData: any,
data: any,
cart: any
): any;
/** Validates fulfillment options (always returns true) */
validateOption(data: any): boolean;
/** Indicates whether service can calculate shipping prices */
canCalculate(): boolean; // Always returns false
/** Throws error - manual service cannot calculate prices */
calculatePrice(): never;
/** Creates order fulfillment (no-operation) */
createOrder(): Promise<{}>;
/** Creates return fulfillment (no-operation) */
createReturn(): Promise<{}>;
/** Creates fulfillment (no-operation) */
createFulfillment(): Promise<{}>;
/** Cancels fulfillment (no-operation) */
cancelFulfillment(): Promise<{}>;
/** Retrieves fulfillment documents (returns empty array) */
retrieveDocuments(): Promise<[]>;
}The service provides two predefined fulfillment options.
/**
* Fulfillment option configuration
*/
interface FulfillmentOption {
/** Unique identifier for the fulfillment option */
id: string;
/** Optional flag indicating if this is a return option */
is_return?: boolean;
}Available Options:
{ id: "manual-fulfillment" } - Standard fulfillment option{ id: "manual-fulfillment-return", is_return: true } - Return fulfillment optionStatic identifier used by Medusa to register the fulfillment provider.
/**
* Static identifier for the manual fulfillment provider
* Used by Medusa to register and identify this provider
*/
static identifier = "manual";Methods for validating fulfillment data and options.
/**
* Validates fulfillment data before processing
* @param optionData - Option-specific data (unused)
* @param data - Fulfillment data to validate
* @param cart - Cart object (unused)
* @returns The original data unchanged
*/
validateFulfillmentData(optionData: any, data: any, cart: any): any;
/**
* Validates fulfillment options
* @param data - Option data to validate
* @returns true - Always validates successfully
*/
validateOption(data: any): boolean;Methods related to shipping price calculation (not supported).
/**
* Indicates whether this service can calculate shipping prices
* @returns false - Manual service cannot calculate prices
*/
canCalculate(): boolean;
/**
* Attempts to calculate shipping price
* @throws Error - Manual Fulfillment service cannot calculatePrice
*/
calculatePrice(): never;Core fulfillment operations that return empty promises.
/**
* Creates an order fulfillment
* @returns Promise resolving to empty object
*/
createOrder(): Promise<{}>;
/**
* Creates a return fulfillment
* @returns Promise resolving to empty object
*/
createReturn(): Promise<{}>;
/**
* Creates a fulfillment
* @returns Promise resolving to empty object
*/
createFulfillment(): Promise<{}>;
/**
* Cancels a fulfillment
* @returns Promise resolving to empty object
*/
cancelFulfillment(): Promise<{}>;
/**
* Retrieves fulfillment documents
* @returns Promise resolving to empty array
*/
retrieveDocuments(): Promise<[]>;/**
* Base class from medusa-interfaces
*/
abstract class FulfillmentService {
// Base implementation provided by Medusa
}The service throws one specific error:
Error("Manual Fulfillment service cannot calculatePrice") when attempting to calculate pricesAll other methods are designed to succeed with no-operation implementations.