# Introduction

## CFConfig Manual - Version 1.0.0

![CFConfig](/files/-LA-UonDlO3LyfYYrdhx)

Welcome to the CFConfig Manual. CFConfig is a project aimed at helping server admins and developers alike manage the configuration of their favorite CF engine.

## Versioning

CFConfig is maintained under the [Semantic Versioning](http://semver.org) guidelines as much as possible. Releases will be numbered in the following format:

```
<major>.<minor>.<patch>.<buildID>
```

And constructed with the following guidelines:

* Breaking backward compatibility bumps the major (and resets the minor and patch)
* New additions without breaking backward compatibility bumps the minor (and resets the patch)
* Bug fixes and misc changes bumps the patch

## License

CFConfig is open source and bound to the [LGPL v3 GNU LESSER GENERAL PUBLIC LICENSE](https://www.gnu.org/licenses/lgpl.html)

* Copyright by Ortus Solutions, Corp

> **Info** The CFConfig Websites, Documentation, logo and content have a separate license and they are a separate entity.

## Discussion & Help

The CFConfig help and discussion group can be found here: <https://community.ortussolutions.com/c/communities/commandbox/>

## Reporting a Bug

We all make mistakes from time to time :) So why not let us know about it and help us out? We also love pull requests, so please star us and fork us:

* <https://github.com/ortus-solutions/cfconfig>
* <https://github.com/ortus-solutions/commandbox-cfconfig>
* <https://ortussolutions.atlassian.net/browse/CFConfig>

## Professional Open Source

![Ortus Solutions, Corp](/files/SPOY223imlbKnAfJUN53)

CFConfig is professional open-source software backed by [Ortus Solutions, Corp](http://www.ortussolutions.com/services) offering services like:

* Custom Development
* Professional Support & Mentoring
* Training
* Server Tuning
* Security Hardening
* Code Reviews
* [Much More](http://www.ortussolutions.com/services)

## Resources

* Official Site: <http://www.ortussolutions.com/products/commandbox>
* Source Code:
  * <https://github.com/ortus-solutions/commandbox-cfconfig>
  * <https://github.com/ortus-solutions/cfconfig>
* Bug Tracker: <https://ortussolutions.atlassian.net/browse/CFConfig>
* Twitter: [@ortussolutions](http://www.twitter.com/ortussolutions)
* Facebook: <https://www.facebook.com/ortussolutions>
* Google+: <https://google.com/+OrtusSolutions>
* Vimeo Channel: <https://www.cfcasts.com/series/cf-config/> (as well as older videos at <http://vimeo.com/channels/commandbox>)

### HONOR GOES TO GOD ABOVE ALL

Because of His grace, this project exists. If you don't like this, don't read it; it's not for you.

> "Therefore being justified by **faith**, we have peace with God through our Lord Jesus Christ: By whom also we have access by **faith** into this **grace** wherein we stand, and rejoice in hope of the glory of God." Romans 5:5


# About This Book

The source code for this book is hosted in GitHub: <https://github.com/ortus-docs/cfconfig-docs>. You can freely contribute to it and submit pull requests. The contents of this book is copyright by [Ortus Solutions, Corp](http://www.ortussolutions.com) and cannot be altered or reproduced without author's consent. All content is provided *"As-Is"* and can be freely distributed.

* The majority of code examples in this book are done in `cfscript`.

## External Trademarks & Copyrights

Flash, Flex, ColdFusion, and Adobe are registered trademarks and copyrights of Adobe Systems, Inc. Railo is a trademark and copyright of Railo Technologies, GmbH. Lucee is a trademark and copyright of Lucee Association Switzerland.

## Notice of Liability

The information in this book is distributed “as is”, without warranty. The author and Ortus Solutions, Corp shall not have any liability to any person or entity with respect to loss or damage caused or alleged to be caused directly or indirectly by the content of this training book, software and resources described in it.

## Contributing

We highly encourage contribution to this book and our open source software. The source code for this book can be found in our [GitHub repository](https://github.com/ortus-docs/cfconfig-docs) where you can submit pull requests.

## Charitable Proceeds

15% of the proceeds of this book will go to charity to support orphaned kids in El Salvador - <http://www.harvesting.org/>. So please donate and purchase the printed version of this book, every book sold can help a child for almost 2 months.

### Shalom Children's Home

![](/files/-LA-Up1MDuA1ucUTM07L)

Shalom Children’s Home (<http://www.harvesting.org/>) is one of the ministries that is dear to our hearts located in El Salvador. During the 12-year civil war that ended in 1990, many children were left orphaned or abandoned by parents who fled El Salvador. The Benners saw the need to help these children and received 13 children in 1982. Little by little, more children came on their own, churches and the government brought children to them for care, and the Shalom Children’s Home was founded.

Shalom now cares for over 80 children in El Salvador, from newborns to 18 years old. They receive shelter, clothing, food, medical care, education and life skills training in a Christian environment. The home is supported by a child sponsorship program.

We have personally supported Shalom since 2006; it is a place of blessing for many children in El Salvador that either have no families or have been abandoned. This is good earth to seed and plant.


# Authors

## Brad Wood

Brad grew up in southern Missouri where he systematically disassembled every toy he ever owned which occasionally led to unintentional shock therapy (TVs hold charge long after they've been unplugged, you know) After high school he majored in Computer Science with a music minor at [MidAmerica Nazarene University](http://www.mnu.edu) (Olathe, KS). Today he lives in Kansas City with his wife and three girls where he still disassembles most of his belongings (including automobiles) just with a slightly higher success rate of putting them back together again.) Brad enjoys church, all sorts of international food, and the great outdoors.

Brad has been programming CFML for 12+ years and has used every version of CF since 4.5. He first fell in love with ColdFusion as a way to easily connect a database to his website for dynamic pages. Brad blogs at <http://www.codersrevolution.com> and likes to work on solder-at-home digital and analog circuits with his daughter as well as building projects with Arduino-based microcontrollers.

Brad's CommandBox Snake high score is 141.

## Luis Fernando Majano Lainez

Luis Majano is a Computer Engineer with over 15 years of software development and systems architecture experience. He was born in [San Salvador, El Salvador](http://en.wikipedia.org/wiki/El_Salvador) in the late 70’s, during a period of economical instability and civil war. He lived in El Salvador until 1995 and then moved to Miami, Florida where he completed his Bachelors of Science in Computer Engineering at [Florida International University](http://fiu.edu). Luis resides in Houston, Texas with his beautiful wife Veronica, baby girl Alexia and baby boy Lucas!

He is the CEO of [Ortus Solutions](http://www.ortussolutions.com), a consulting firm specializing in web development, ColdFusion (CFML), Java development and all open source professional services under the ColdBox and ContentBox stack. He is the creator of ColdBox, ContentBox, WireBox, MockBox, LogBox and anything “BOX”, and contributes to many open source ColdFusion projects. He is also the Adobe ColdFusion user group manager for the [Inland Empire](http://www.iecfug.org). You can read his blog at [www.luismajano.com](http://www.luismajano.com)

Luis has a passion for Jesus, tennis, golf, volleyball and anything electronic. Random Author Facts:

* He played volleyball in the Salvadorean National Team at the tender age of 17
* The Lord of the Rings and The Hobbit is something he reads every 5 years. (Geek!)
* His first ever computer was a Texas Instrument TI-86 that his parents gave him in 1986. After some time digesting his very first BASIC book, he had written his own tic-tac-toe game at the age of 9. (Extra geek!)
* He has a geek love for circuits, microcontrollers and overall embedded systems.
* He has of late (during old age) become a fan of running and bike riding with his family.

> Keep Jesus number one in your life and in your heart. I did and it changed my life from desolation, defeat and failure to an abundant life full of love, thankfulness, joy and overwhelming peace. As this world breathes failure and fear upon any life, Jesus brings power, love and a sound mind to everybody!

> “Trust in the LORD with all your heart, and do not lean on your own understanding.” – Proverbs 3:5

## Contributors

* Jorge Reyes - ColdBox Aficionado


# Overview

```
   ____ _____ ____             __ _       
  / ___|  ___/ ___|___  _ __  / _(_) __ _ 
 | |   | |_ | |   / _ \| '_ \| |_| |/ _` |
 | |___|  _|| |__| (_) | | | |  _| | (_| |
  \____|_|   \____\___/|_| |_|_| |_|\__, |
                                    |___/
```

## Overview

CFConfig gives you the ability to manage almost every setting that shows up in the web administrator, but instead of logging into a web interface, you can manage it from the command line by hand or as part of a scripted server setup. You can seamlessly transfer config for all the following:

* CF Mappings
* Datasources
* Mail servers
* Request, session, or application timeouts
* Licensing information (for Adobe)
* Passwords
* Template caching settings
* Basically any settings in the web-based administrator

### Use on any server

CFConfig will work on any CF server regardless of how it was installed. Since it interacts directly with the config files, the server doesn't need to be running. Heck, the server doesn't even need to be installed yet! CFConfig can be used to write out config files before you even start a CommandBox server for the first time.

But it's not just for CommandBox servers. All you need is the folder path to the CF home in your server installation and you can point the CFConfig library at it. This means CFConfig can be used for syncing config across existing servers, standing up docker containers, or provisioning Vagrant VMs.

### How does it work

CFConfig interfaces directly with the XML and property files used by your CF engine to store its configuration. It takes care of translating the config properly so you use the same commands regardless of what engine you're managing the config for. The tool will try hard to figure out the version of ColdFusion or Lucee that you have installed, and there are hints you can give it as well. Both ACF and Lucee also have settings to monitor the config files for changes, so you don't even need to restart the server to pick up your changes.

CFConfig exists in two parts:

* A service layer for reading, writing, and storing configuration for all CF engines.
* A set of scriptable commands built on top of CommandBox CLI.

### CFConfig Service Layer

The heart of CFConfig is a standalone module that provides a set of models and services for interacting with configuration files for all CF engines. This library allows for reading, writing, storing, and diffing configuration. This is an underlying service layer meant to have other tools built on top of it.

The CFConfig services do not require CommandBox but can be used on their own and provide a nice, fluent API for managing configs. They do not use RDS and don't need the server to be running. The services just need access to the installation folder for a server to locate its config files.

#### Features at a Glance

* Generic JSON storage of any CF engine's settings
* Engine-specific mappings for all major engines to convert their config to and from the generic JSON format
* Export config from a server as a backup
* Import config to a server to speed/automate setup
* Copy config from one server to another. Servers could be different engines–i.e., copy config from Adobe CF11 to Lucee 5.
* Merge config from multiple servers together. Ex: combine several Lucee web contexts into a single config (mappings, datasources, etc.)

### CFConfig CLI

The CLI portion of CFConfig wraps up the services layer into a CommandBox module that provides command line access to all the features above, but from your native OS shell, bash scripts, automations, or Docker/Vagrant/Heroku provisioners.

The CFConfig CLI also has a deep integration with CommandBox servers, making it very easy to manage their configuration.

#### Features at a Glance

* Provides a native CLI tool for managing server configuration
* Scriptable for automated server setup
* Provides complete command help built-in
* Tight integration with CommandBox servers


# Getting Started Guide

To use CFConfig, you can install it into CommandBox easily like so.

```
CommandBox> install commandbox-cfconfig
```

Now that you've got the tool installed you can dig into the command help to see where to go from there. Here's a quick overview of some of the commands. Run the built-in command help for more info on each one.

These commands will work on any CF engine and if you run them from the root of CommandBox server they will "just work" as it will "find" the server for you. To run these commands against another type of server, you'd need to specify a folder path for the "from" or "to" parameters that pointed to the server home directories.

## View a setting

```
CommandBox> cfconfig show requestTimeout
```

## Set a setting

```
CommandBox> cfconfig set requestTimeout=0,0,10,0
```

## View all settings for a server

```
CommandBox> cfconfig show
```

## Add, list, and delete a CF Mapping

```
CommandBox> cfconfig cfmapping save virtual=/foo physical=C:/bar
CommandBox> cfconfig cfmapping list
CommandBox> cfconfig cfmapping delete /foo
```

## Add, list and delete a datasource

```
CommandBox> cfconfig datasource save name=myDSN dbdriver=mysql host=localhost port=3306 database=myDB username=brad password=foobar
CommandBox> cfconfig datasource list
CommandBox> cfconfig datasource delete myDSN
```

## Export all settings from a server

```
CommandBox> cfconfig export .CFConfig.json
```

## Import settings into a server

```
CommandBox> cfconfig import .CFConfig.json
```

## Transfer settings from one server to another

```
CommandBox> cfconfig transfer from=oneServer to=anotherServer
```

## Diff all the settings between two servers

```
CommandBox> cfconfig diff from=oneServer to=anotherServer
CommandBox> cfconfig diff to=anotherServerName
CommandBox> cfconfig diff to=anotherServerName --fromOnly
CommandBox> cfconfig diff to=anotherServerName --toOnly
CommandBox> cfconfig diff to=anotherServerName --valuesDiffer
```


# Supported Engines

CFConfig covers most of the common settings you'll find in Adobe and Lucee servers. This includes datasources, CF Mappings, Lucee caches, mail servers, logging settings, debugging settings, event gateways (Adobe), scheduled tasks (Adobe), and custom tag paths.

If you find a setting or feature which is not supported, please send a pull request. If you don't have time for a pull request, please [enter a ticket](https://ortussolutions.atlassian.net/projects/CFCONFIG) so we can track remaining features.

Here's an overview of what's supported.

* **BoxLang 1.x**
* **Lucee 6.x**
* **Lucee 5.x**
* **Lucee 4.x**
* **Adobe CF 2025**
* **Adobe CF 2023**
* **Adobe CF 2021**
* **Adobe CF 2018**
* **Adobe CF 2016**
* **Adobe CF 11**
* **Adobe CF 10**
* **Adobe CF 9**
* **Railo 4.x**

## Sponsored Support

If there is an engine/version or specific setting that's very important to you, Ortus is happy to have sponsored features. Please [contact us](https://www.ortussolutions.com/#contact) if you'd like to sponsor a feature.


# Config Items

CFConfig supports over 200 individual config items. Here's the list of settings that CFConfig can manage

```javascript
// One of the strings "never", "once", "always"
name='inspectTemplate' type='string'
// Number of templates to cache
name='templateCacheSize' type='numeric'
// Number of queries to keep in cache
name='queryCacheSize' type='numeric'
// true/false When checked, at server level internal cache is used to store cached queries. By default, cached queries are stored in QUERY region supported by Ehcache.
// Adobe-only
name='QueryInternalCacheEnabled' type='boolean'
// True/false
name='componentCacheEnabled' type='boolean'
// True/false
name='saveClassFiles' type='boolean'
// True/false
name='UDFTypeChecking' type='boolean'
// true/false
name='nullSupport' type='boolean'
// true/false
name='dotNotationUpperCase' type='boolean'
// true/false
name='suppressWhitespaceBeforecfargument' type='string'
// One of the strings "standard", "small", "strict"
name='scopeCascading' type='string'
// True/false
name='searchResultsets' type='boolean'

name='baseComponent' type='string'

// Charts can be cached either in memory or to disk. In memory caching is faster, but more memory intensive. (0 = memory cache, 1 = disk cache)
name='chartCacheType' type='numeric'
// Time-to-Live of each chart in seconds
name='chartCacheTTL' type='numeric'
// Maximum number of cached images
name='chartCacheSize' type='numeric'
// Disk cache location.  When caching to disk, specifies the directory in which to store the generated charts.
name='chartCacheDiskLocation' type='string'

// Ex: en_US
name='thisLocale' type='string'
// Ex: 	America/Chicago
name='thisTimeZone' type='string'
// Ex: 	pool.ntp.org
name='timeServer' type='string'
// true/false
name='useTimeServer' type='boolean'

// Ex: windows-1252 (Lucee: Default character used to read templates (*.cfm and *.cfc files))
name='templateCharset' type='string'
// Ex: UTF-8 (Lucee: Default character set for output streams, form-, url-, and cgi scope variables and reading/writing the header)
name='webCharset' type='string'
// Ex: windows-1252 (Default character set for reading from/writing to various resources)
name='resourceCharset' type='string'

// One of the strings "cfml", "j2ee"
name='sessionType' type='string'
// True/false
name='mergeURLAndForm' type='boolean'
// True/false
name='applicationManagement' type='boolean'
// True/false
name='sessionManagement' type='boolean'
// True/false
name='clientManagement' type='boolean'
// True/false
name='domainCookies' type='boolean'
// True/false
name='clientCookies' type='boolean'

// Cookie Timeout - Number of seconds
name='sessionCookieTimeout' type='numeric'
// True/false
name='sessionCookieHTTPOnly' type='boolean'
// True/false
name='sessionCookieSecure' type='boolean'
// Disable updating ColdFusion internal cookies using ColdFusion tags/functions - True/false
name='sessionCookieDisableUpdate' type='boolean'
// Cookie Samesite default value - Strict, Lax, None, or empty string
name='sessionCookieSamesite' type='string'


// One of the strings "classic", "modern"
name='localScopeMode' type='string'
// True/false
name='CGIReadOnly' type='string'
// Timespan Ex: 0,5,30,0
name='sessionTimeout' type='string'
// Timespan Ex: 0,5,30,0
name='applicationTimeout' type='string'
// Timespan Ex: 0,5,30,0
name='sessionMaximumTimeout' type='string'
// Timespan Ex: 0,5,30,0
name='applicationMaximumTimeout' type='string'

// One of the strings "none", "mixed", "modern", "classic"
name='applicationListener' type='string'
/* One of the strings
* "curr2root" - Current dir to web root (Lucee and Adobe [option 2])
* "curr" - Current dir only (Lucee only)
* "root" - Only in web root (Lucee only)
* "currorroot" -  Current dir or web root (Lucee and Adobe [option 3])
* "curr2driveroot" - Current dir to drive root (Adobe only [option 1])
*/
name='applicationMode' type='string'

// Timespan Ex: 0,5,30,0
name='clientTimeout' type='string'
// One of the strings "memory", "file", "cookie", <cache-name>, <datasource-name>
name='sessionStorage' type='string'
// One of the strings "memory", "file", "cookie", <cache-name>, <datasource-name>, "Registry"
name='clientStorage' type='string'
// Number of minutes between client storage purge.  Not to be less tham 30 minutes.
name='clientStoragePurgeInterval' type='numeric'
// A struct of valid client storage locations including registry, cookie, and any configured datasources. Only used by Adobe.
name='clientStorageLocations' type='struct'
// TODO: Add functions/commands to manage this manually.

// One of the strings "memory", "redis".  Adobe use only.
name='sessionStorageLocation' type='string'
// Passowrd for session storage.  Adobe use only.
name='sessionStoragePassword' type='string'
// Host for session storage.  Adobe use only.
name='sessionStorageHost' type='string'
// Timeout in ms for session storage.  Adobe use only.
name='sessionStorageTimeout' type='numeric'
// Port for session storage  Adobe use only.
name='sessionStoragePort' type='numeric'


// Timespan Ex: 0,5,30,0
name='requestTimeout' type='string'
// True/false
name='requestTimeoutEnabled' type='boolean'

// Blocked file extensions for CFFile uploads
name='blockedExtForFileUpload' type='string'
// "none", "all" or a comma-delimited list with some combination of "cgi", "cookie", "form", "url".
name='scriptProtect' type='string'
// True/false
name='perAppSettingsEnabled' type='boolean'
// True/false
name='useUUIDForCFToken' type='boolean'
// True/false
name='requestTimeoutInURL' type='boolean'
// One of the strings "off", "simple", "smart"
// for Lucee backwards compat, you can use "regular", "white-space", "white-space-pref" which map to the above options in the same order.
// Adobe only has on and off so "simple" and "smart" both just map to the fetaure being on.
name='whitespaceManagement' type='string'
// True/false
name='compression' type='boolean'
// True/false
name='supressContentForCFCRemoting' type='boolean'
// True/false
name='bufferTagBodyOutput' type='boolean'
// Key is datasource name, value is struct of properties
name='datasources' type='struct'

// Preserve single quotes (") in the SQL defined with the tag cfquery (Lucee only)
name='datasourcePreserveSingleQuotes' type='boolean'

// Array of structs of properties.  Mail servers are uniquely identified by host
name='mailServers' type='array'
/**
 * Custom tags have no unique identifier.  In Adobe, there's a made up
 * "virtual" key of /WEB-INF/customtags(somenumber), but it's never shown
 * topside.  In Lucee, you *could* name a path, but you don't have to.
 *
 * We're going to store in an array, and later if we need to determine
 * uniqueness, we'll manufacture a key to do so.
 */
// Array of tag paths ( value struct of properties )
name='customTagPaths' type='array'

// Search for custom tags in subdirectories. (Lucee only)
name='customTagSearchSubdirectories' type='boolean'
// Search in the caller directory for the custom tag. (Lucee only)
name='customTagSearchLocal' type='boolean'
//  component path is cached and not resolved again.  (Lucee only)
name='customTagCachePaths' type='boolean'
// These are the extensions used for Custom Tags, in the order they are searched.
name='customTagExtensions' type='string'

// Component search paths (Lucee only). Key is the name
name='componentPaths' type='struct'

// Encoding to use for mail. Ex: UTF-8
name='mailDefaultEncoding' type='string'
// True/false enable mail spooling
name='mailSpoolEnable' type='boolean'
// Number of seconds for interval
name='mailSpoolInterval' type='numeric'
// Number of seconds to wait for mail server response
name='mailConnectionTimeout' type='numeric'
// True/false to allow downloading attachments for undelivered emails
name='mailDownloadUndeliveredAttachments' type='boolean'
// Sign messages with cert
name='mailSignMesssage' type='boolean'
// Path to keystore
name='mailSignKeystore' type='string'
// Password to the keystore
name='mailSignKeystorePassword' type='string'
// Alias of the key with which the certificcate and private key is stored in keystore. The supported type is JKS (java key store) and pkcs12.
name='mailSignKeyAlias' type='string'
// Password with which the private key is stored.
name='mailSignKeyPassword' type='string'
// true/false Log all mail messages sent by ColdFusion.  Select this check box to save the To, From, and Subject fields of messages to a log file.
name='mailLogEnabled' type='boolean'
// Error Log Severity. Select the type of SMTP-related error messages to log.
// One of the strings "debug", "information", "warning", "error"
name='mailLogSeverity' type='string'
// Number of mail delivery threads
name='mailMaxThreads' type='numeric'


// Key is virtual path, value is struct of properties
name='CFMappings' type='struct'
// Key is log name, value is struct of properties
name='loggers' type='struct'
// Enable HTTP status codes.  ColdFusion sets an error status code of 404 if the template is not found and an error status code of 500 for server errors.
name='errorStatusCode' type='boolean'
// True/false
name='disableInternalCFJavaComponents' type='boolean'

// True/false
name='secureJSON' type='boolean'
// A string representing the JSON prefx like "//"
name='secureJSONPrefix' type='string'

// Number of KB for buffer size (1024)
name='maxOutputBufferSize' type='numeric'

// True/false
name='inMemoryFileSystemEnabled' type='boolean'
// Number of MB for in memory file system
name='inMemoryFileSystemLimit' type='numeric'
// Number of MB for in memory application file system
name='inMemoryFileSystemAppLimit' type='numeric'

// True/false
name='watchConfigFilesForChangesEnabled' type='boolean'
// Number of seconds
name='watchConfigFilesForChangesInterval' type='numeric'
// List of file extensions. Ex: "xml,properties"
name='watchConfigFilesForChangesExtensions' type='string'

// True/false
name='allowExtraAttributesInAttrColl' type='boolean'
// True/false
name='disallowUnamedAppScope' type='boolean'
// True/false
name='allowApplicationVarsInServletContext' type='boolean'
// Number of minutes
name='CFaaSGeneratedFilesExpiryTime' type='numeric'
// Absolute path to store index files for ORM search.
name='ORMSearchIndexDirectory' type='string'
// default path (relative to the web root) to the directory containing the cfform.js file.
name='CFFormScriptDirectory' type='string'
// Your Google maps API key
name='googleMapKey' type='string'

// Your Lucee API key (Lucee doesn't use it, but ForgeBox will since it's passed to extension providers)
name='APIKey' type='string'

// True/false
name='serverCFCEenabled' type='boolean'
// Specify the absolute path to a CFC having onServerStart() method, like "c:\server.cfc". Or specify a dot delimited CFC path under webroot, like "a.b.server". By default, ColdFusion will look for server.cfc under webroot.
name='serverCFC' type='string'

// file extensions as a comma separated list which gets compiled when used in the CFInclude tag * for all.
name='compileExtForCFInclude' type='string'

/* Error Templates. One of the strings
* "default" - Standard handling for engine. Blank for Adobe, "error.cfm" for Lucee/Railo. Not secure.
* "secure" - Uses the engine's secure template.
* "neo" - Mirrors appearance of default Adobe handler (Lucee/Railo)
* Alternatively, you can provide the path to a custom template
*/
name='generalErrorTemplate' type='string'
name='missingErrorTemplate' type='string'

// Maximum number of parameters in a POST request sent to the server.
name='postParametersLimit' type='numeric'
// Limits the amount of data in MB that can be posted to the server in a single request.
name='postSizeLimit' type='numeric'
// Requests smaller than the specified limit in MB are not handled by the throttle.
name='throttleThreshold' type='numeric'
// Limits total memory size in MB for the throttle
name='totalThrottleMemory' type='numeric'


// Maximum number of simultaneous Template requests
name='maxTemplateRequests' type='numeric'
// Maximum number of simultaneous Flash Remoting requests
name='maxFlashRemotingRequests' type='numeric'
// Maximum number of simultaneous Web Service requests
name='maxWebServiceRequests' type='numeric'
// Maximum number of simultaneous CFC function requests
name='maxCFCFunctionRequests' type='numeric'
// Maximum number of simultaneous Report threads
name='maxReportRequests' type='numeric'
// Maximum number of threads available for CFTHREAD
name='maxCFThreads' type='numeric'
// Timeout requests waiting in queue after XX seconds
name='requestQueueTimeout' type='numeric'
// Request Queue Timeout Page
name='requestQueueTimeoutPage' type='string'

// Key is cache connection name, value is struct of properties
name='caches' type='struct'

// Array of extension provider URLs (strings)
name='extensionProviders' type='array'

// name of default Object cache connection
name='cacheDefaultObject' type='string'
// name of default function cache connection
name='cacheDefaultFunction' type='string'
// name of default Template cache connection
name='cacheDefaultTemplate' type='string'
// name of default Query cache connection
name='cacheDefaultQuery' type='string'
// name of default Resource cache connection
name='cacheDefaultResource' type='string'
// name of default Include cache connection
name='cacheDefaultInclude' type='string'
// name of default File cache connection
name='cacheDefaultFile' type='string'
// name of default HTTP cache connection
name='cacheDefaultHTTP' type='string'
// name of default WebService cache connection
name='cacheDefaultWebservice' type='string'

// Line Debugger Settings - Allow Line Debugging
name='lineDebuggerEnabled' type='boolean'
// Line Debugger Settings - Debugger Port
name='lineDebuggerPort' type='numeric'
// Line Debugger Settings - Maximum Simultaneous Debugging Sessions:
name='lineDebuggerMaxSessions' type='numeric'

// Enable robust error information (Adobe only)
name='robustExceptionEnabled' type='boolean'
// Enable Ajax debugging window (Adobe only)
name='ajaxDebugWindowEnabled' type='boolean'
// "Enable Request Debugging Output" in Adobe / "Enable debugging" in Lucee
name='debuggingEnabled' type='boolean'
// Remote DOM Inspection Settings
name='weinreRemoteInspectionEnabled' type='boolean'
// Report Execution Times
name='debuggingReportExecutionTimes' type='boolean'

// Database Activity - Select this option to log the database activity for the SQL Query events and Stored Procedure events. - Lucee only
name='debuggingDBEnabled' type='boolean'
// Exceptions - Select this option to log all exceptions raised for the request. - Lucee only
name='debuggingExceptionsEnabled' type='boolean'
// Query Usage - Select this option to log the query usage information. - Lucee only
name='debuggingQueryUsageEnabled' type='boolean'
// Tracing -Select this option to log trace event information. Tracing lets a developer track program flow and efficiency through the use of the CFTRACE tag.  - Lucee only
name='debuggingTracingEnabled' type='boolean'
// Dump - Select this option to enable output produced with help of the tag cfdump and send to debugging. - Lucee only
name='debuggingDumpEnabled' type='boolean'
// Timer - Select this option to show timer event information. Timers let a developer track the execution time of the code between the start and end tags of the CFTIMER tag. - Lucee only
name='debuggingTimerEnabled' type='boolean'
// Implicit variable Access - Select this option to log all accesses to scopes, queries and threads that happens implicit (cascaded). - Lucee only
name='debuggingImplicitVariableAccessEnabled' type='boolean'

// Maximum Logged Requests - Lucee only
name='debuggingMaxLoggedRequests' type='numeric'


// Debugging Templates - Lucee only
name='debuggingTemplates' type='struct'

// Debugging Highlight templates taking longer than the following ms
name='debuggingReportExecutionTimesMinimum' type='numeric'
// Debugging Use the following output mode for long template request execution times
name='debuggingReportExecutionTimesTemplate' type='string'
// Debugging Output Format (dockable.cfm, classic.cfm)
name='debuggingTemplate' type='string'
// Debugging show General debug information
name='debuggingShowGeneral' type='boolean'
// Debugging show Database Activity
name='debuggingShowDatabase' type='boolean'
// Debugging show Exception Information
name='debuggingShowException' type='boolean'
// Debugging show Tracing Information
name='debuggingShowTrace' type='boolean'
// Debugging show Timer Information
name='debuggingShowTimer' type='boolean'
// Debugging Flash Form Compile Errors and Messages
name='debuggingShowFlashFormCompileErrors' type='boolean'
// Debugging Variables. Select this option to enable variable reporting.
name='debuggingShowVariables' type='boolean'
// Debugging include application vars
name='debuggingShowVariableApplication' type='boolean'
// Debugging include cgi vars
name='debuggingShowVariableCGI' type='boolean'
// Debugging include client vars
name='debuggingShowVariableClient' type='boolean'
// Debugging include cookie vars
name='debuggingShowVariableCookie' type='boolean'
// Debugging include form vars
name='debuggingShowVariableForm' type='boolean'
// Debugging include request vars
name='debuggingShowVariableRequest' type='boolean'
// Debugging include server vars
name='debuggingShowVariableServer' type='boolean'
// Debugging include session vars
name='debuggingShowVariableSession' type='boolean'
// Debugging include URL vars
name='debuggingShowVariableURL' type='boolean'
// Debugging IP Addresses
name='debuggingIPList' type='string'

// Monitoring Service Port (Only used by Adobe CF)
// The port for the monitoring service to bind to
name='monitoringServicePort' type='numeric'
// The host for the monitoring service to bind to
// See https://tracker.adobe.com/#/view/CF-4202562
name='monitoringServiceHost' type='string'

// .NET Services (Only used by Adobe CF)
// Java port for .NET services
name='dotNetPort' type='numeric'
// .Net port of JNBridge for .NET services
name='dotNetClientPort' type='numeric'
// Install path to the .NET services
name='dotNetInstallDir' type='string'
// Protocol for the .NET services.  Possible options: TCP, ??
name='dotNetProtocol' type='string'

// Log directory
name='logDirectory' type='string'
// Maximum file size  (In KB)
name='logMaxFileSize' type='numeric'
// Maximum number of archives
name='logMaxArchives' type='numeric'
// Log slow pages taking longer than
name='logSlowRequestsEnabled' type='boolean'
// Number of seconds threshold for logging slow pages
name='logSlowRequestsThreshold' type='numeric'
// Log all CORBA calls
name='logCORBACalls' type='boolean'
// Adobe && UNIX ONLY - Use operating system logging facilities
name='logSysLogEnabled' type='boolean'

// Array of disabled log file names (Adobe CF only)
name='logFilesDisabled' type='array'

// PDF Service Managers (Adobe CF only)
name='PDFServiceManagers' type='struct'

// TODO:
//name='externalizeStrings' type='string'
//name='restMappings' type='array'
//name='componentBase' type='string'
//name='componentAutoImport' type='string'
//name='componentSearchLocal' type='boolean'
//name='componentImplicitNotation' type='boolean'
//name='cfxTags' type='string'


// Enable logging for scheduled tasks
name='schedulerLoggingEnabled' type='boolean'
name='schedulerClusterDatasource' type='string'
name='schedulerLogFileExtensions' type='string'
name='scheduledTasks' type='struct'

// Enable Event Gateway Services
name='eventGatewayEnabled' type='boolean'
// Maximum number of events to queue
name='eventGatewayMaxQueueSize' type='numeric'
// Event Gateway Processing Threads
name='eventGatewayThreadpoolSize' type='numeric'
// Event Gateways > Gateway Instances
name='eventGatewayInstances' type='array'
// Services > Event Gateway - Lucee specific
// Lucee and Adobe event gateways are very different and cannot be transfered between engines.  As such, they are stored separately
name='eventGatewaysLucee' type='struct'
// Event Gateways > Gateway Types
name='eventGatewayConfigurations' type='array'

// Enable WebSocket Service
name='websocketEnabled' type='boolean'


// Enable Flash remoting
name='FlashRemotingEnable' type='boolean'
//  Enable Remote Adobe LiveCycle Data Management access
name='flexDataServicesEnable' type='boolean'
// Enable RMI over SSL for Data Management
name='RMISSLEnable' type='boolean'
// RMI SSL Keystore
name='RMISSLKeystore' type='string'
// RMI SSL Keystore Password
name='RMISSLKeystorePassword' type='string'

// Plain text admin password
name='adminPassword' type='string'
// Plain text admin RDS password
name='adminRDSPassword' type='string'
// True/false is RDS enabled?
name='adminRDSEnabled' type='boolean'
// Plain text default password for new Lucee web context
name='adminPasswordDefault' type='string'
// hashed salted password for Lucee
name='hspw' type='string'
// hashed password for Lucee/Railo
name='pw' type='string'
// Salt for admin password in Lucee
name='adminSalt' type='string'
// hashed salted default password for new Lucee web context
name='defaultHspw' type='string'
// hashed default password for new Lucee/Railo web context
name='defaultPw' type='string'


// Password required for admin
name='adminLoginRequired' type='boolean'
// Password required for RDS
name='adminRDSLoginRequired' type='boolean'
// user ID required for admin login. False means just a password is required
name='adminUserIDRequired' type='boolean'
// user ID required for RDS login. False means just a password is required
name='adminRDSUserIDRequired' type='boolean'
// Default/root admin user ID
name='adminRootUserID' type='string'
// Allow more than one user to be logged into the same userID at once in the admin
name='adminAllowConcurrentLogin' type='boolean'
// Enable sandbox security
name='sandboxEnabled' type='boolean'

// define the access for reading data from the admin. One of the strings open, closed, or protected
name='adminAccessWrite' type='string'
// define the access for writing data from the admin. One of the strings open, closed, or protected
name='adminAccessRead' type='string'


// List of allowed IPs for exposed services.  Formatted like 1.2.3.4,5.6.7.*
name='servicesAllowedIPList' type='string'
// List of allowed IPs for admin access.  Formatted like 1.2.3.4,5.6.7.*
name='adminAllowedIPList' type='string'
// Enable secure profile.  Note, fipping this flag doesn't actually change any of the security settings.  It really just tracks the fact that you've enabled it at some point.
name='secureProfileEnabled' type='boolean'

// System output streams - Lucee only
// values are strings indicating target stream (default,null,class:<class>,file:<file>)
name='systemOut' type='string'
name='systemErr' type='string'

// TODO: adminUsers array (AuthorizedUsers)
// TODO: sandboxes (contexts)

// License key (only used for Adobe)
name='license' type='string'
// Previous license key (required for an upgrade license key)
name='previousLicense' type='string'


// TODO: Figure out what hashing algorithms each version of ACF use, and share the
// same setting so the hashes passwords are as portable as possible

// hashed admin password for Adobe CF11
// TODO: Need to get 10, 11, 2016, and 2018 ironed out here.
name='ACF11Password' type='string'
// hashed RDS password for Adobe CF11
name='ACF11RDSPassword' type='string'

// Automatically Check for Updates. Select to automatically check for updates at every login.
name='updateCheckOnLoginEnable' type='boolean'
// Check for updates every X days Enable
name='updateCheckOnScheduleEnable' type='boolean'
// Number of days between updates
name='updateCheckOnScheduleDays' type='numeric'
// If updates are available, send email notification to (comma-delimited list)
name='updateCheckOnScheduleToAddress' type='string'
// If updates are available, send email notification from
name='updateCheckOnScheduleFromAddress' type='string'
// Update site URL
name='updateSiteURL' type='string'
// Update check proxy host
name='updateProxyHost' type='string'
// Update check proxy port
name='updateProxyPort' type='numeric'
// Update check proxy username
name='updateProxyUsername' type='string'
// Update check proxy password
name='updateProxyPassword' type='string'

```


# Installation

The CFConfig CLI lives on ForgeBox and can be installed into CommandBox with the following command:

```
CommandBox> install commandbox-cfconfig
```

If you do not have CommandBox installed, have no fear! CommandBox is a single binary that will run on Mac, Linux, or Windows. Please visit our CommandBox docs and you'll have it installed in a jiffy.

<https://commandbox.ortusbooks.com/setup/installation>

## Requirements

The only requirement for the CFConfig CLI is [CommandBox](https://commandbox.ortusbooks.com/setup/installation) 3.6.0 or higher.

## Updating CFConfig

CFConfig is under active development and changing on a regular basis. To make sure you have the latest version installed, you can simply `cd` into the CFML home directory of your CommandBox install and use the regular package `update` command. This will pull in minor and patch updates but not major version changes.

```
update --system
```

If you have a pre-release version of CFConfig or need to upgrade to a new major version, use this command:

```
install commandbox-cfconfig --force
```


# Usage

## Specifying a Server Home

CFConfig must determine the server(s) on which to operate, which will either be a web context or a server context. CFConfig will determine the server as follows:

1. By default, when the `to` or `from` parameters are not present, CFConfig will use the current working directory, assuming it is the web root for an Embedded CommandBox Server (see below).
2. You provide a file path to the server home by using the `to` and/or `from` parameters.
3. You provide the name of a previously-started CommandBox server, using `to` and/or `from` parameters (see [CommandBox Managing Servers](https://commandbox.ortusbooks.com/embedded-server/manage-servers)).

### Lucee 6/7

The folder containing the `/context/.CFConfig.json` file. An example would be:

```bash
C:/lucee/tomcat/lucee-server/ 
cfconfig export from=C:/lucee/tomcat/lucee-server/ fromFormat=luceeServer to=myconfig.json
```

### Lucee 4/5 Server Context

The folder containing the `/context/lucee-server.xml` file. An example would be:

```bash
C:/lucee/tomcat/lucee-server/

cfconfig export from=C:/lucee/tomcat/lucee-server/ to=myconfig.json
```

### Lucee 4/5 Web Context

The folder containing the `lucee-web.xml.cfm` file. An example would be:

```bash
<webroot>C:/myapp/WEB-INF/lucee/

cfconfig export from=C:/myapp/WEB-INF/lucee/ to=myconfig.json
```

### Adobe 9/10/11/2016/2018/2021/2023/2025 CF Home

The `cfusion` folder that contains the `lib/neo-runtime.xml` file. An example would be:

```bash
C:/ColdFusion2023/cfusion/

cfconfig export from=C:/ColdFusion2025/cfusion/ to=myconfig.json
```

### JSON File

Just provide the path to the JSON file. This is auto-detected if the path ends in `.json`. An example would be:

```bash
C:/path/to/myConfig.json
```

## Server Format (engine/version)

Every command with a `to` and/or `from` parameter also has a matching `toFormat` and/or `fromFormat` parameter. In most cases, you don't need to provide this. If you are pointing to an existing CommandBox server, or typical server installation, CFConfig will examine the files in the CF home to determine what engine and version it is. However, if you are writing files to an empty or non-existent directory, you'll need to tell CFConfig what format to write them in.

Format is specified as `engine@version` where:

* `engine` is the name of the CF engine.
* `version` is a semantic version number representing the engine version.

Possible engine values are:

* **luceeWeb** - Lucee web context.
* **luceeServer** - Lucee server context (Default for Lucee servers).
* **adobe** - Adobe server.
* **railoWeb** - Railo web context.
* **railoServer** - Railo server context.

Here are some examples of server formats:

* adobe\@10
* adobe\@11.0.10
* luceeServer\@5
* luceeWeb\@4.5

### Embedded CommandBox Server

If you run CFConfig from the web root of a CommandBox embedded server, you do not need to specify the `from` or `to` parameters to reference it, and CFConfig will automatically default to the `luceeServer` format, which operates on the server context. If you wish to interact with the web context (which has little distinction in a CommandBox server since there's only one web context per server), you will need to provide the explicit `luceeWeb` format by using either the `toFormat` or `fromFormat` parameters.

```bash
cfconfig show fromFormat=luceeWeb
```

This example assumes you are running CFConfig from the web root of an embedded server:

```bash
cfconfig import from=config_admin.json toFormat=luceeWeb
```

## ModCFML and Web Contexts

When using ModCFML, Lucee can have more than one web context. When using the `fromFormat` or `toFormat` of `luceeWeb`, you will be interacting with the Lucee web context associated with the default web root. To interact with a specific Lucee web context, specify the web root in the format name like so:

```bash
cfconfig export fromFormat=luceeWeb-/path/to/webroot/site1 to=.cfconfig-web-site1.json
cfconfig export fromFormat=luceeWeb-/path/to/webroot/site2 to=.cfconfig-web-site2.json
```


# CommandBox Server Interceptors

The CommandBox CLI module will automatically register several interceptors that listen for server starts and stops. This allows you to automate your configuration without needing to manually load settings.

This functionality only applies to servers that are started in CommandBox. Examples would be using CommandBox for local development, deploying our Docker images or Heroku buildpacks.

You can use the CFConfig commands to manually import/export configuration on 'standard' CF installs, but these automatic interceptors here don't apply.

* [Server Start](/using-the-cli/commandbox-server-interceptors/server-start) -- Import config automatically when the server starts
* [Server Stop](/using-the-cli/commandbox-server-interceptors/server-stop) -- Optionally export config when the server stops


# Server Start

Every time a server starts, CFConfig will load configuration into your server by convention. For Lucee servers, settings go in the server context by default. Since each CommandBox Lucee server only has a single web context, the differentiation is mostly moot.

## Import from JSON file

CFConfig will attempt to locate a JSON file containing exported server configuration. If it finds a JSON file, it will import it into the starting server as it comes up.

Here are the locations CFConfig will look for a JSON file and the order it will look for them in. After CFConfig files a JSON file in one location, it stops looking.

### Environment Variable

If an environment variable exists with the name `CFConfigFile`, `CFConfigWeb`, or `CFConfigServer` it will be used as an absolute path to the JSON file or a relative path in relation to the web root. An example of setting this in Windows would be:

```
C:/> SETX cfconfigfile "C:/path/to/myConfig.json"
C:/> SETX cfconfigweb "C:/path/to/myConfig-web.json"
C:/> SETX cfconfigserver "C:/path/to/myConfig-server.json"
```

And on Unix...

```
$> cfconfigfile=C:/path/to/myConfig.json
$> cfconfigweb=C:/path/to/myConfig-web.json
$> cfconfigserver=C:/path/to/myConfig-server.json
$> export cfconfigfile
$> export cfconfigweb
$> export cfconfigserver
```

*Note: CommandBox won't pick up new environment variables in Windows until you close and reopen the shell.*

It's not necessary to use `cfconfigfile` and `cfconfigsever` at the same time since they do the same thing. They are both provided for consistency. If you use both, they will all be imported!

Technically, you can also use one of the following env vars to do the same thing since CommandBox supports a generic syntax to override any `server.json` property, but given the options above, it's not necessary to use these unless you want to or specifically want to override the settings in the `server.json`.

```bash
box_server_cfconfig_file=settings.json
box_server_cfconfig_web=settings.json
box_server_cfconfig_server=settings.json
```

### `server.json` properties

If there is a `CFConfig` property in your `server.json` file, it will be used to help control how your JSON configs are imported. All JSON file paths can be absolute or relative paths from the folder the `server.json` lives in.

```javascript
"cfconfig" : {
   // Single JSON file to import into Adobe or the Lucee server context
   "file" : "path/to/file.json",
   // Same as "file" but for consistency with Lucee
   "server" : "path/to/file.json",
   // Will load into lucee/railo web context
   "web" : "path/to/file.json",
   // Import scheduled tasks as paused
   "pauseTasks" : true
},
// Backwards compat fallback
"CFConfigFile" : "path/to/file.json"
"CFConfigPauseTasks": true
```

Note, you would never need to use all the properties above at the same time. The two top level ones are only supported for backwards compatibility. For an Adobe server, or a Lucee server in which you only care about importing settings into the server context, you can just use `cfconfig.file` . For a Lucee server in which you want to import settings into the server AND web context, you can use `cfconfig.server` and `cfconfig.web`.

### ModCFML Support for Lucee Contexts

If you are using CommandBox's ModCFML support with Lucee, there can be a different set of settings for each Lucee web context. By default, all "web" settings will load into the web context that corresponds with the default CommandBox web root for the server. You can specify a JSON file for each web context in your `server.json` like so:

```json
{
    "cfconfig":{
        "server":".cfconfig-server.json",
        "web-/path/to/webroot/site1":".cfconfig-web-site1.json",
        "web-/path/to/webroot/site2":".cfconfig-web-site2.json",
        "web-/path/to/webroot/site3":".cfconfig-web-site3.json"
    }
}
```

The path to the web root as Lucee sees it is appended to the `web` key after a hyphen (`-`). CFConfig will pre-emptively create the web context folders based on the hash of the web root.

## Multiple JSON files

Since there are several overlapping conventions, it's possible to have more than one JSON file. For example, you could have a `cfconfigfile` environment variable set as well as a `cfconfig.file` key in your `server.json`. In this case, BOTH JSON files will be imported. When there are two more JSON files being imported into the same web or server context, the first file will be an overwrite as usual and all subsequent files will be imported in "append" mode so they add to the settings in the previous file.

### `.cfconfig.json` File in Webroot

if and ONLY IF no other settings (env vars, or `server.json` properties) are found to specify a JSON file to import, CFConfig will look for the following files in the web root by convention.

* `.cfconfig.json` - Use this for Adobe or for Lucee's server context
* `.cfconfig-web.json` Use this for the Lucee web context
* `.cfconfig-server.json` Use this for the Lucee server context (same as `.cfconfig.json` )

If the only convention file found for an Adobe server is `.cfconfig-web.json` or `.cfconfig-server.json`, it will still be used but just imported into Adobe's single context.

## Set Individual Settings

If you don't want to have a full JSON file, but just want to set some ad-hoc settings, you can do this via environment variables. These will load regardless of whether a JSON file was imported so it gives you a chance to override specifics like passwords. Environment variables are also perfect for cloud environments and Docker images.

### Variable names

When a server starts up, all environment variables will be looped over, and all the ones that start with `cfconfig_` will be used. The naming format is `cfconfig_xxx` where `xxx` is the name of a valid config item such as `adminPassword` or `requestTimeout`.

Here's an example of what setting that up on Windows might look like:

```
C:/> SETX cfconfig_adminPassword "myCoolPass123"
```

And on Unix...

```
$> cfconfig_adminPassword=myCoolPass123
$> export cfconfig_adminPassword
```

Now, every time a CommandBox server is started on this machine, that password will be loaded in, even if a previous JSON import had another password.

If you want to target the web context for your settings, you can use the syntax `cfconfig_web_xxx` like so:

```bash
cfconfig_web_adminPassword=myPass
```

## Admin Passwords on Lucee

As a safety precaution, any time an `adminPassword` setting is present in an auto-imported JSON file or a `cfconfig_adminPassword` environment variable is set on a Lucee server, the server start interceptor will set that password into the web context as well as the default server context. This is to prevent a production server getting deployed with no password on the web context.

This only applies to the auto server start interceptors documented on this page. if you manually run a `cfconfig import` or `cfconfig set` command, it's up to you to also set things like passwords into the server and web contexts.

## Production Password Protection

On both Lucee and Adobe servers, when the server profile is set to `production`, CFConfig will not allow your sever to start with an empty password or with the Adobe default password of `commandbox`. If any of those scenarios are detection in a `production` profile, CFConfig will set a random password and output it in the verbose console logs for you to refer to later.


# Server Stop

## Server Stop

If you are keeping your CF configuration in source control via a local JSON file, you may wish for the JSON file to automatically "track" your CF engine's settings. Otherwise, any changes you make to your CF setting in the web administrator will be lost the next time you start your server and your JSON config is imported again.

### Enable

To enable this feature, add a global config setting in CommandBox like so:

```bash
config set modules.commandbox-cfconfig.exportOnStop=true
```

The setting above defaults to off. You need to opt in to this behavior.

## Usage

Every time a server does a graceful shutdown via the `server stop` command, a suitable JSON file will be searched for using the same criteria used by the server start interceptor. If a JSON file is found, the current engine's config will be exported into it.

Lucee’s server and web contexts will export into the matching JSON files, if they exist. If there is more than one JSON file declared for a given context, the first will be used.

This ensures that any changes you make in the CF admin will be reflected back in your JSON file so you can commit it and share it with your coworkers. Please note, stopping a server from your system tray does not currently fire the server stop interceptors.

### Disable

If you want to make temporary changes to your CF settings that you don't want to commit, use your source control to revert the JSON back, or turn the setting back off like so:

```bash
config set modules.commandbox-cfconfig.exportOnStop=false
```


# Command Overview

Here's an overview of all the commands available to the CFConfig CLI. There are sub-pages for each of these commands with additional details.

## Manage All Configs

### `cfconfig export`

Extracts all configuration from a server to a location of your choice.

### `cfconfig import`

Imports all configuration from a location of your choice into a server. Like `export`, but spelled different.

### `cfconfig transfer`

Moves all configuration from a location of your choice to another location of your choice. Like `import` and `export` but pronounced different.

### `cfconfig diff`

Shows a diff of every setting that's different between two servers or a server and a JSON file.

## Manage Individual Configs

### `cfconfig set`

Sets or overwrites a single setting on a server.

### `cfconfig show`

Views a single setting on a server.

## Manage Datasources

### `cfconfig datasource list`

List all datasources.

### `cfconfig datasource save`

Add or update a datasource by name

### `cfconfig datasource delete`

Remove a datasource by name.

## Manage CF Mappings

### `cfconfig cfmapping list`

List all CF mappings

### `cfconfig cfmapping save`

Add or update a CF mapping by virtual path.

### `cfconfig cfmapping delete`

Remove a CF mapping by virtual path.

## Manage Lucee/Railo Caches

### `cfconfig cache list`

List all caches in a Lucee/Railo server.

### `cfconfig cache save`

Add or update a cache by name.

### `cfconfig cache delete`

Remove a cache by name.

## Manage Mail Servers

### `cfconfig mailserver list`

List all mail servers on a server.

### `cfconfig mailserver save`

Add or update a mail server by host.

### `cfconfig mailserver delete`

Delete a mail server by host.

## Manage Custom Tag Paths

### `cfconfig customtagpath list`

List all Custom Tag paths

### `cfconfig customtagpath save`

Save a Custom Tag path

### `cfconfig customtagpath delete`

Delete a Custom Tag path

## Event Gateway Configuration

### `cfconfig eventgatewayconfig list`

List all Event Gateway Configurations

### `cfconfig eventgatewayconfig save`

Add or update an Event Gateway Configuration

### `cfconfig eventgatewayconfig delete`

Delete an Event Gateway Configuration

## Event Gateway Instances

### `cfconfig eventgatewayinstance list`

List all Event Gateway Instances

### `cfconfig eventgatewayinstance save`

Add or update an Event Gateway Instance

### `cfconfig eventgatewayinstance delete`

Delete an Event Gateway Instance

## Lucee Loggers

### `cfconfig logger list`

List all Lucee Loggers

### `cfconfig logger save`

Add or update a Lucee Logger

### `cfconfig logger delete`

Delete a Lucee Logger

## Scheduled Tasks

### `cfconfig task list`

List all Scheduled Tasks

### `cfconfig task save`

Add or update a Scheduled Task

### `cfconfig task delete`

Delete a Scheduled Task


# Export Settings

Export configuration from a server. If you don't specify a `to`, we look for a CommandBox server using the current working directory. Only rely on this if you have a single CommandBox server running in the current directory.

```
cfconfig export myConfig.json
cfconfig export from=serverNameToExportFrom to=myconfig.json
cfconfig export from=/path/to/server/home to=myconfig.json
```

All the same rules for engine format and version apply.

```
cfconfig export to=/path/to/.CFConfig.json from=/path/to/server/home fromFormat=luceeServer@5.1
```

The version number can be left off `toFormat` and `fromFormat` when reading or writing to a CFConfig JSON file or a CommandBox server since we already know the version. If you don't specify a Lucee web or Server context, we default to server. Use a format of "luceeWeb" to switch.

```
cfconfig export to=myConfig.json fromFormat=luceeWeb
```

In some situations you might need to alter the data being imported such as with Scheduled Tasks that you might not want to run on the target server. Adding the `--pauseTasks` flag will import the scheduled tasks in the paused state.

### IncludeList and excludeList

You can customize what config settings are transferred with the `includeList` and `excludeList` params. If at least one include pattern is provided, **only** matching settings will be included. Nested keys such as `datasources.myDSN` or `mailservers[1]` can be used. You may also use basic wildcards in your pattern. A single `*` will match any number of chars inside a key name. A double `**` will match any number of nested keys.

```bash
# Include all settings starting with "event"
cfconfig export to=.CFConfig.json includeList=event*
# Exclude all keys called "password" regardless of what struct they are in
cfconfig export to=.CFConfig.json excludeList=**.password
```

### Append flag

Use the `append` parameter to merge incoming data with any data already present. For example, if a server already has one datasource defined, and you import a JSON file with 2 more unique datasources, the `--append` flag will not remove the pre-existing one.

```bash
cfconfig export to=.CFConfig.json includeList=datasources --append
```

### JSON Expansion Replacements

If you usually replace sensitive or volatile information in a JSON export with env var expansions like `${DB_PASSWORD},` you can do this automatically my supplying one or more replace mappings. The key is a regular expression to match a key in the format of `datasources.myDSN.password` and the value is the name of the env var to use. The values will be written to a `.env` file in the current working directory. You can override this path with the `dotenvFile` param, or pass an empty string to disable it from being written.

```bash
cfconfig export to=.CFConfig.json replace:datasources\.myDSN\.password=DB_PASSWORD
```

As the value is a regular expression, you can use backreferences like `\1` in your env var to make them dynamic.\
This example would create env vars such as `DB_MYDSN_PASSWORD` where `MYDSN` is your actual datasource name.

```bash
cfconfig export to=.CFConfig.json replace:datasources\.(.*)\.password=DB_\1_PASSWORD
```

Any valid regex is possible for some clever replacements. This example would create env vars such as `DB_MYDSN_PORT`, `DB_MYDSN_HOST`, and `DB_MDSN_DATABASE`

```bash
cfconfig export to=.CFConfig.json replace:datasources\.(.*)\.(password|class|port|host|database)=DB_\1_\2 dotenvFile=../../settings.properties
```

To avoid having to pass these replacements every time you transfer your config, you can set then as a global setting for the `commandbox-cfconfig` module.

```bash
# Replace all mail server passwords with ${MAIL_PASSWORD}
config set modules.commandbox-cfconfig.JSONExpansions[mailServers.*.password]=MAIL_PASSWORD
# Dynamically replace with ${DB_MYDSN_password}, ${DB_MYDSN_CLASS}, ${DB_MYDSN_PORT}, etc
config set modules.commandbox-cfconfig.JSONExpansions[datasources\.(.*)\.(password|class|port|host|database)]=DB_\1_\2
# Use default env var name for all settings starting with "requestTimeout" and replace with ${REQUEST_TIMEOUT} and ${REQUEST_TIMEOUT_ENABLED}
config set modules.commandbox-cfconfig.JSONExpansions[requestTimeout.*]=
```

{% hint style="info" %}
Note, the `config set` syntax shown above require at least CommandBox 5.4.0
{% endhint %}


# Import Settings

Import configuration to a server. If you don't specify a `to`, we look for a CommandBox server using the current working directory. Only rely on this if you have a single CommandBox server running in the current directory.

```
cfconfig import myConfig.json
cfconfig import to=serverName from=myConfig.json
cfconfig import to=/path/to/server/home from=myConfig.json
```

All the same rules for engine format and version apply.

```
cfconfig import from=/path/to/.CFConfig.json to=/path/to/server/home toFormat=luceeServer@5.1
```

The version number can be left off `toFormat` and `fromFormat` when reading or writing to a CFConfig JSON file or a CommandBox server since we already know the version. If you don't specify a Lucee web or Server context, we default to server. Use a format of `luceeWeb` to switch.

```
cfconfig import from=myConfig.json toFormat=luceeWeb
```

### IncludeList and excludeList

You can customize what config settings are transferred with the `includeList` and `excludeList` params. If at least one include pattern is provided, **only** matching settings will be included. Nested keys such as `datasources.myDSN` or `mailservers[1]` can be used. You may also use basic wildcards in your pattern. A single `*` will match any number of chars inside a key name. A double `**` will match any number of nested keys.

```bash
# Include all settings starting with "event"
cfconfig import from=.CFConfig.json includeList=event*
# Exclude all keys called "password" regardless of what struct they are in
cfconfig import from=.CFConfig.json excludeList=**.password
```

### Append flag

Use the `append` parameter to merge incoming data with any data already present. For example, if a server already has one datasource defined, and you import a JSON file with 2 more unique datasources, the `--append` flag will not remove the pre-existing one.

```bash
cfconfig import from=.CFConfig.json includeList=datasources --append
```


# Transfer Settings

Transfer configuration from one location/server to another. If you don't specify a from or to, we look for a CommandBox server using the current working directory. Only rely on this if you have a single CommandBox server running in the current directory. You must specify at least a `from` or a `to`.

Note the two servers do not need to be the same kind. CFConfig will translate the config for you.

```
cfconfig transfer from=servername to=anotherServername
cfconfig transfer from=serverName
cfconfig transfer to=serverName
cfconfig transfer from=/path/to/server/home to=/path/to/another/server/home
cfconfig transfer from=/path/to/server/home
cfconfig transfer to=/path/to/server/home
```

All the same rules for engine format and version apply.

```
cfconfig transfer from=/path/to/.CFConfig.json to=/path/to/server/home toFormat=luceeServer@5.1
```

The version number can be left off `toFormat` and `fromFormat` when reading or writing to a CFConfig JSON file or a CommandBox server since we already know the version. If you don't specify a Lucee web or Server context, we default to server. Use a format of `luceeWeb` to switch.

### IncludeList and excludeList

You can customize what config settings are transferred with the `includeList` and `excludeList` params. If at least one include pattern is provided, **only** matching settings will be included. Nested keys such as `datasources.myDSN` or `mailservers[1]` can be used. You may also use basic wildcards in your pattern. A single `*` will match any number of chars inside a key name. A double `**` will match any number of nested keys.

```bash
# Include all settings starting with "event"
cfconfig transfer from=.CFConfig.json includeList=event*
# Exclude all keys called "password" regardless of what struct they are in
cfconfig transfer from=.CFConfig.json excludeList=**.password
```

### Append flag

Use the `append` parameter to merge incoming data with any data already present. For example, if a server already has one datasource defined, and you import a JSON file with 2 more unique datasources, the `--append` flag will not remove the pre-existing one.

```bash
cfconfig transfer from=.CFConfig.json includeList=datasources --append
```

### JSON Expansion Replacements

If you usually replace sensitive or volatile information in a JSON export with env var expansions like `${DB_PASSWORD},` you can do this automatically my supplying one or more replace mappings. The key is a regular expression to match a key in the format of `datasources.myDSN.password` and the value is the name of the env var to use. The values will be written to a `.env` file in the current working directory. You can override this path with the `dotenvFile` param, or pass an empty string to disable it from being written.

```bash
cfconfig transfer to=.CFConfig.json replace:datasources\.myDSN\.password=DB_PASSWORD
```

As the value is a regular expression, you can use backreferences like `\1` in your env var to make them dynamic.\
This example would create env vars such as `DB_MYDSN_PASSWORD` where `MYDSN` is your actual datasource name.

```bash
cfconfig tranfser to=.CFConfig.json replace:datasources\.(.*)\.password=DB_\1_PASSWORD
```

Any valid regex is possible for some clever replacements. This example would create env vars such as `DB_MYDSN_PORT`, `DB_MYDSN_HOST`, and `DB_MDSN_DATABASE`

```bash
cfconfig tranfser to=.CFConfig.json replace:datasources\.(.*)\.(password|class|port|host|database)=DB_\1_\2 dotenvFile=../../settings.properties
```

To avoid having to pass these replacements every time you transfer your config, you can set then as a global setting for the `commandbox-cfconfig` module.

```bash
# Replace all mail server passwords with ${MAIL_PASSWORD}
config set modules.commandbox-cfconfig.JSONExpansions[mailServers.*.password]=MAIL_PASSWORD
# Dynamically replace with ${DB_MYDSN_password}, ${DB_MYDSN_CLASS}, ${DB_MYDSN_PORT}, etc
config set modules.commandbox-cfconfig.JSONExpansions[datasources\.(.*)\.(password|class|port|host|database)]=DB_\1_\2
# Use default env var name for all settings starting with "requestTimeout" and replace with ${REQUEST_TIMEOUT} and ${REQUEST_TIMEOUT_ENABLED}
config set modules.commandbox-cfconfig.JSONExpansions[requestTimeout.*]=
```

{% hint style="info" %}
Note, the `config set` syntax shown above require at least CommandBox 5.4.0
{% endhint %}


# Diff Settings

You can diff any two locations, meaning two servers, two JSON files, a server and a JSON file, etc.

```
cfconfig diff server1 server2
cfconfig diff file1.json file2.json
cfconfig diff servername file.json
cfconfig diff from=path/to/servers1/home to=path/to/server2/home
```

You can even filter what config settings you see:

```
cfconfig diff to=serverName --all
cfconfig diff to=serverName --valuesDiffer --toOnly --fromOnly
```

## Diff Reports

The `cfconfig diff` commandbox has the ability to export HTML and PDF files. The contents of the report will exactly match what displays in the CLI. So any flags you apply such as `--toOnly` will also filter the report output. This can be handy for historical purposes or just to get the data into a format that's easier to read than the CLI.

To generate an HTML report:

```bash
cfconfig diff to=... from=... HTMLReportPath=folder/
cfconfig diff to=... from=... HTMLReportPath=folder/file.html
```

To generate a PDF report:

```bash
cfconfig diff to=... from=... PDFReportPath=folder/
cfconfig diff to=... from=... PDFReportPath=folder/file.pdf
```

You can generate both HTML and PDF at the same time if you like. If you don't provide a filename, one is created for you with the following format:

```
cfconfig-diff-report-YYYY-MM-DD-HHMMSS.[html|pdf]
```

The report directory is also created for you if it doesn't exist.

Remember, you can get funky and generate clever report names on the fly such as:

```bash
cfconfig diff ... PDFreportpath="Daily-Report-`#now | #dayOfWeek | #dayOfWeekAsString`.pdf"
```

This would give you a name like `Daily-Report-Thursday.pdf`! Existing files are overwritten.


# Set/View Settings

## View all configuration

```bash
cfconfig show
cfconfig show serverName
cfconfig show /path/to/server/install/home
```

## View a specific configuration setting

```bash
cfconfig show requestTimeout
cfconfig show requestTimeout serverName
cfconfig show requestTimeout /path/to/server/install/home adobe@11
```

## Set a configuration setting

Note, this command requires named parameters.

```bash
cfconfig set adminPassword=commandbox
cfconfig set adminPassword=commandbox to=serverName
cfconfig set adminPassword=commandbox to=/path/to/server/install/home toFormat=adobe@11
```

You can actually use CFConfig set to manage the static contents of a JSON export. The JSON file is, after all, just another location you can read from or write to.

```bash
# Pull current config from server into JSON file
cfconfig export myConfig.json
# Edit JSON file directly
cfconfig set adminPassword=commandbox to=myConfig.json
```

### Using "deep" property names

The `cfconfig set` and `cfconfig show` commands work the same as `package set/show` in that you can use "deep" keys to access nested properties.

```bash
cfconfig show datasources.myDSN
cfconfig show mailServers[1].port
cfconfig set loggers.deploy.level=debug
cfconfig set datasources.myDSN.password=myPass
```

Keep in mind that examples such as the last line above can create invalid config if you don't already have a datasource called `myDSN`.  If you're needing to create new complex objects, or you're not sure if they will exist, use the other CFConfig namespaces like `cfconfig datasource save` which will ensure complete settings are saved.


# Manage Datasources

There are three commands to manage datasources.

## List all datasources

```
cfconfig datasource list
cfconfig datasource list from=serverName
cfconfig datasource list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig datasource list --JSON
```

## Edit an existing or create a new datasource

Add a new datasource or update an existing datasource. Existing datasources will be matched based on the name. Valid dbdriver options are

* **MSSQL** -- SQL Server driver
* **MSSQL2** -- jTDS driver
* **PostgreSql**
* **Oracle**
* **Other** -- Custom JDBC URL
* **MySQL**

```
cfconfig datasource save name=myDSN dbdriver=mysql host=localhost port=3306 database=myDB username=brad password=foobar
cfconfig datasource save name=myDS ... to=serverName
cfconfig datasource save name=myDS ... to=/path/to/server/home
```

## Delete a datasource

Identify the datasource uniquely by the name.

```
cfconfig datasource delete foo
cfconfig datasource delete foo serverName
cfconfig datasource delete foo /path/to/server/home
```


# Manage CF Mappings

There are three commands to manage CF mappings.

## List all CF Mappings

```bash
cfconfig cfmapping list
cfconfig cfmapping list from=serverName
cfconfig cfmapping list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig cfmapping list --JSON
```

## Edit an existing or create a new CF Mapping

Add a new CF mapping or update an existing CF Mapping. Existing mappings will be matched based on the virtual path.

```
cfconfig cfmapping save /foo C:/foo/bar
cfconfig cfmapping save virtual=/foo physical=C:/foo/bar to=serverName
cfconfig cfmapping save virtual=/foo physical=C:/foo/bar to=/path/to/server/home
```

## Delete a CF Mapping

Identify the mapping uniquely by the virtual path.

```
cfconfig cfmapping delete /foo
cfconfig cfmapping delete /foo serverName
cfconfig cfmapping delete /foo /path/to/server/home
```


# Manage Caches

There are three commands to manage Lucee/Railo caches.

## List existing caches

```bash
# Lucee server context of the CommandBox server in the current directory
cfconfig cache list

# Lucee web context of the CommandBox server in the current directory
cfconfig cache list fromFormat=luceeWeb

# Target a CommandBox server by name
cfconfig cache list from=serverName

# Target an externally installed server
cfconfig cache list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig cache list --JSON
```

## Edit an existing or create a new cache

Add a new cache or update an existing cache. Existing caches will be matched based on the name. You can use a the `type` parameter as a shortcut for specifying the full Java class, which may change between versions.

```
cfconfig cache save myCache RAM
cfconfig cache save name=myOtherCache type=EHCache
cfconfig cache save name=myCache type=EHCache  to=serverName
cfconfig cache save name=myCache type=RAM to=/path/to/server/home
```

Alternatively, specify the full class name.

```
cfconfig cache save myCache lucee.runtime.cache.ram.RamCache
cfconfig cache save name=myCache class=lucee.runtime.cache.ram.RamCache to=serverName
cfconfig cache save name=myCache class=lucee.runtime.cache.ram.RamCache to=/path/to/server/home
```

If your cache provider expects custom properties, pass them as additional parameters to this command prefixed with the text `custom:`. This requires named parameters, of course.

```
cfconfig cache save name=myCache type=RAM custom:timeToIdleSeconds=0 custom:timeToLiveSeconds=0
```

## Delete an existing cache

Identify the cache uniquely by the name.

```
cfconfig cache delete myCache
cfconfig cache delete myCache serverName
cfconfig cache delete myCache /path/to/server/home
```


# Manage Mail Servers

There are three commands to manage Mail Servers.

## List existing mail servers

```
cfconfig mailserver list
cfconfig mailserver list from=serverName
cfconfig mailserver list from==/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig mailserver list --JSON
```

## Edit an existing or create a new mail server

Add a new mail server or update an existing mail server. Existing mail servers will be matched based on the host name.

```
cfconfig mailserver save smtp.server.com
cfconfig mailserver save smtp=smtp.server.com to=serverName
cfconfig mailserver save smtp=smtp.server.com to=/path/to/server/home
```

## Delete an existing mail server

Identify the mail server uniquely by the host name.

```
cfconfig mailserver delete /foo
cfconfig mailserver delete /foo serverName
cfconfig mailserver delete /foo /path/to/server/home
```


# Manage Event Gateway Configuration

Event Gateway Configurations are currently only supported for Adobe ColdFusion. Please contact us if you'd like to sponsor this feature.

## List all Event Gateway Configurations

```
cfconfig eventgatewayconfig list
cfconfig eventgatewayconfig list from=serverName
cfconfig eventgatewayconfig list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig eventgatewayconfig list --JSON
```

## Add or update an Event Gateway Configuration

```
cfconfig eventgatewayconfig save myType "description of gateway" "java.class" 30 true
cfconfig eventgatewayconfig save type=myType description="description of gateway" class="java.class" starttimeout=30 killontimeout=true to=serverName
cfconfig eventgatewayconfig save type=myType description="description of gateway" class="java.class" starttimeout=30 killontimeout=true to=/path/to/server/home
```

## Delete an Event Gateway Configuration

```
cfconfig eventgatewayconfig delete myType
cfconfig eventgatewayconfig delete myType serverName
cfconfig eventgatewayconfig delete myType /path/to/server/home
```


# Manage Event Gateway Instances

Event Gateway Instances are currently only supported for Adobe ColdFusion. Please contact us if you'd like to sponsor this feature.

## List all Event Gateway Instances

```
cfconfig eventgatewayinstance list
cfconfig eventgatewayinstance list from=serverName
cfconfig eventgatewayinstance list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig eventgatewayinstance list --JSON
```

## Add or update an Event Gateway Instance

```
cfconfig eventgatewayinstance save myInstanceId myType "/path1/some.cfc,/path2/code.cfc"
cfconfig eventgatewayinstance save gatewayId=myInstanceId type=myType cfcPaths="/path1/some.cfc,/path2/code.cfc" configurationPath="path3" to=serverName
cfconfig eventgatewayinstance save gatewayId=myInstanceId type=myType cfcPaths="/path1/some.cfc,/path2/code.cfc" configurationPath="path3" to=/path/to/server/home
```

## Delete an Event Gateway Instance

```
cfconfig eventgatewayinstance delete myInstanceId
cfconfig eventgatewayinstance delete myInstanceId serverName
cfconfig eventgatewayinstance delete myInstanceId /path/to/server/home
```


# Manage Lucee Loggers

## List all Lucee Loggers

```
cfconfig logger list
cfconfig logger list from=serverName
cfconfig logger list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig logger list --JSON
```

## Add or update a Lucee Logger

```
cfconfig logger save name=application appender=resource appenderArguments:path={lucee-config}/logs/application.log
cfconfig logger save name=application appender=resource appenderArguments:path={lucee-config}/logs/application.log to=serverName
cfconfig logger save name=application appender=resource appenderArguments:path={lucee-config}/logs/application.log to=/path/to/server/home
```

## Delete a Lucee Logger

```
cfconfig logger delete application
cfconfig logger delete application serverName
cfconfig logger delete application /path/to/server/home
```


# Manage Scheduled Tasks

Scheduled tasks are supported for both Lucee Server and Adobe ColdFusion. Both engines have some features which are not supported by the other. Check the parameter descriptions in the command help for `cfconfig task save` for more info.

All CFConfig commands when run against a Lucee server will default to the `fromFormat` or `toFormat` to `luceeServer`. These commands are a notable exception-- since scheduled tasks can only be imported into a Lucee web context, all commands in the `cfconfig task` namespace will default to the `luceeWeb` for Lucee servers.

## List all Scheduled Tasks

```
cfconfig task list
cfconfig task list from=serverName
cfconfig task list from=/path/to/server/home
```

To receive the data back as JSON, use the `--JSON` flag.

```
cfconfig task list --JSON
```

## Add or update a Scheduled Task

```
cfconfig task save myTask http://www.google.com Once 4/13/2018 "5:00 PM"
cfconfig task save task=myTask url=http://www.google.com interval=Once startDate=4/13/2018 startTime="5:00 PM" to=serverName
cfconfig task save task=myTask url=http://www.google.com interval=Once startDate=4/13/2018 startTime="5:00 PM" to=/path/to/server/home
```

## Delete a Scheduled Task

```
cfconfig task delete myTask
cfconfig task delete myTask serverName
cfconfig task delete myTask /path/to/server/home
```


# JSON File Storage

CFConfig can represent the settings for any server in a generic JSON format. Even though some settings may be specific to Lucee Server or Adobe ColdFusion, the JSON format itself is generic and can be used on any engine. Any settings that don't apply to a given engine will simply be ignored. For example, caches or mail servers past the first one are ignored when importing to Adobe ColdFusion.

## Automatically Deploying Saved Configurations

You may choose to commit your settings to a file called `.cfconfig.json` in the webroot, which will cause them to automatically get loaded in on every server start. This is the easiest way to share configuration with your coworkers. One issue with this may be that you don't want the JSON file in your web root in case it accidentally gets moved to a production server and is directly accessible. Web servers such as Apache will not serve files starting with `.` by default, but other web servers will happily share those "hidden" files. You can work around this by placing the JSON file outside the web root and using the `cfconfigFile` property in your `server.json` to point to it. You can use relative paths like `../build/mySettings.json`.

## Separate Lucee/Railo Server/Web Context Config

If you are using Lucee or Railo and wish to have separate config for your server and web contexts, you can use the following file names which will be found by convention if there are no other settings (env vars or `server.json` keys specifying JSON file locations).

* `.cfconfig-server.json`
* `.cfconfig-web.json`

If these files exist for an Adobe server, they will still be used.

### Dynamic Values and System Settings

Another potential issue with the JSON file is that you may have secrets in your config such as passwords that you don't want to commit to your repo or that are simply different on some servers. You can manage this by using CommandBox's "system settings" which will expand any environment variables in your CFConfig JSON file. System settings are in the format `${mySetting}` and would look like so in your JSON file:

```json
{
  "adminPassword": "${LOCAL_DEV_CF_PASS}"
}
```

That JSON above would automatically replace the `adminPassword` setting with the value of an environment variable called `LOCAL_DEV_CF_PASS`.

You can take this a step further and provide a default value so the env var is just an override. The format is `${name:default}`.

```json
{
  "requestTimeout": "${LOCAL_DEV_TIMEOUT:0,0,1,0}"
}
```

That JSON above would set the request timeout to 1 minute unless it was overridden by an env var called `LOCAL_DEV_TIMEOUT`.

### Handling Scheduled Tasks

Since scheduled tasks are also managed by CFConfig, any running tasks on the source server will be running on the destination server which might not be desirable. Use these techniques to pause tasks:

In conjunction with the `cfconfigFile` in `server.json`, set the `CFConfigPauseTasks` setting to true with `server set CFConfigPauseTasks=true`.

When using CFConfig to import, export, or transfer settings, use the `--pauseTasks` flag, i.e., `cfconfig import myConfig.json --pauseTasks`.


# Env Var Overrides

Every [Config Setting](/the-basics/config-items) can be overridden by convention by creating environment variables in the shell where you run `box`. This is ideal for Docker containers or CI builds where you want to easily set one-off settings and not require an entire JSON file. You can set these as actual environment variables or [Java system properties of the CLI](https://commandbox.ortusbooks.com/usage/execution#ad-hoc-java-properties-for-the-cli). Env vars are loaded AFTER any `.cfconfig.json` files have been loaded by convention and will override any settings in the JSON. They are not case-sensitive.

The variable must start with the text `cfconfig_` and will be followed by the name of the setting.

```bash
cfconfig_adminPassword=myPass
```

For nested settings inside a struct or array, you can use underscores to represent dots. Note the following will error if there is not already a datasource named `myDSN` in the server.

```bash
cfconfig_datasources_myDSN_password=myPass
```

The overrides are applied using the same mechanism that the `cfconfig set` command uses, which means you can also pass JSON directly for complex values.

```bash
# JSON which will be parsed
cfconfig_mailServers=[{"port":"25","smtp":"localhost2"}]
```

On OS's like Windows which allow for any manner of special characters, you can provide any string which would also be valid for the `config set` command. Ex:

```bash
# dot-delimited keys
cfconfig_datasources.myDSN.password=myPass
# array indexes too
cfconfig_mailServers[1].smtp=mail.server.com
```

When you provide JSON, the `append` flag will be set to true when adding the configuration to what's already in CommandBox.

Overridden env vars will **not** be written to any `.cfconfig.json` file and will be lost when box stops. They will also take precedence and override any explicit settings already set.

## Target a Lucee/Railo specific server/web context

If you want to specify a setting via an env var that targets a web context, you can use the following conventions:

```bash
# Default (server context)
cfconfig_requestTimeout=...

# Force web context.  (On adobe, just loaded normally)
cfconfig_web_requestTimeout=...

# Force server context- same as default. (On adobe, just loaded normally)
cfconfig_server_requestTimeout=...
```


# Installation

If you just want to use the core CFConfig services outside the CLI, you can install them like so:

```bash
install cfconfig-services
```

The code in this library has only been tested on Lucee and likely doesn't work on Adobe ColdFusion. If anyone wants to make it compatible, feel free to try but beware of tons of use of the Elvis operator, reliance on sorted JSON structs, and some specific WDDX behavior.


# Component Overview

Here are the main components in the project

#### BaseConfig.cfc

This class represents the configuration of a CF engine. It is agnostic and doesn't contain any particular behavior for a specific engine.\
Not all the data it stores applies to every engine though. The `BaseConfig.cfc` is not capable of reading or writing the config, it merely holds the data in a generic manner. If you want to read or write to/from a specific engine's format, you'll need to create one of the engine-specific subclasses, all of which extend `BaseConfig.cfc`.

#### Engine-specific mappers

* **JSONConfig.cfc** - Engine-agnostic JSON format
* **Lucee4Server.cfc** - Lucee 4.x server context
* **Lucee4Web.cfc** - Lucee 4.x web context
* **Lucee5Server.cfc** - Lucee 5.x server context
* **Lucee5Web.cfc** - Lucee 5.x web context
* **Railo4Server.cfc** - Railo 4.x server context
* **Railo4Web.cfc** - Railo 4.x web context
* **Adobe9.cfc** - Adobe ColdFusion 9
* **Adobe10.cfc** - Adobe ColdFusion 10
* **Adobe11.cfc** - Adobe ColdFusion 11
* **Adobe2016.cfc** - Adobe Coldfusion 2016
* **Adobe2018.cfc** - Adobe Coldfusion 2018

### Usage

Each of the components above supports these public methods:

* `setCFHomePath()` - Points to the server home where the config files are to be read or written.
* `read( CFHomePath )` - Extract the config from the files found in the server home. You can override `CFHomePath` here too.
* `write( CFHomePath )` - Write the config out to the files in the server home whether or not they already exist. You can override `CFHomePath` here too.
* `getMemento()` - Return all configuration in as a raw CFML data structure. Useful for passing config values to another instance.
* `setMemento()` - Accept configuration as a raw CFML data structure. Useful for accepting another instance's data.

Create an instance of the component that corresponds to the server that you'd like to read or write config settings from, or the `BaseConfig` class if you want to deal with the generic JSON-based config.


# API Overview

**Create a new JSON configuration file programmatically**

```javascript
JSONConfig = new path.to.JSONConfig()
    .setNullSupport( true )
    .setUseTimeServer( true )
    .setAdminPassword( 'myPass' )
    .addCFMapping( '/foo', '/bar' )
    .write();
```

**Read an existing JSON configuration file**

```javascript
JSONConfig = new path.to.JSONConfig()
    .read( 'test.json' );
```

**Read an existing Lucee 4 server configuration file**

```javascript
lucee4ServerConfig = new path.to.Lucee4ServerConfig()
    .setCFHomePath( expandPath( '/path/to/lucee-server' ) )
    .read();

writeDump( lucee4ServerConfig.getMemento() );
```

**Read an existing JSON config file and load into a Lucee 5 web context**

```javascript
JSONConfig = new path.to.JSONConfig()
    .read( expandPath( '.CFConfig.json' ) );

new path.to.Lucee4WebConfig()
    .setMemento( JSONConfig.getMemento() )        
    .write( expandPath( 'WEB-INF/lucee/' ) );
```

### Notes

The `JSONConfig` will read/write to a JSON file called `.CFConfig.json` by default in the home directory you specify. You can alternatively specify a full path to a JSON file to change the name.

The Lucee 4 and Lucee 5 *web* components expect the `CFHomePath` to be the folder containing the `lucee-web.xml.cfm` file.\
An example would be:

```
<webroot>/WEB-INF/lucee/
```

The Lucee 4 and Lucee 5 *server* components expect the `CFHomePath` to be the `lucee-server` folder containing the `/context/lucee-server.xml` file.\
An example would be:

```
/opt/lucee/lib/lucee-server/
```

The Adobe components expect the `CFHomePath` to be the `cfusion` folder that contains the `lib/neo-runtime.xml` file.\
An example would be:

```
C:/ColdFusion11/cfusion/
```

The code in this library has only been tested on Lucee and likely doesn't work on Adobe ColdFusion. If anyone wants to make it compatible, feel free to try by beware of tons of use of the Elvis operator, reliance on sorted JSON structs, and some specific WDDX behavior.


