diff --git a/res/res_stasis.c b/res/res_stasis.c
index b3ed1731f70957f2b13992572f9fd307269ee5c6..4a11680fbb62593f20f65ca2aff8bcbda167a3f6 100644
--- a/res/res_stasis.c
+++ b/res/res_stasis.c
@@ -24,6 +24,7 @@
  */
 
 /*** MODULEINFO
+	<depend>res_stasis_json_events</depend>
 	<support_level>core</support_level>
  ***/
 
@@ -41,7 +42,7 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
 #include "asterisk/strings.h"
 #include "asterisk/stasis_message_router.h"
 #include "asterisk/callerid.h"
-#include "stasis_http/resource_events.h"
+#include "stasis_json/resource_events.h"
 
 /*! Time to wait for a frame in the application */
 #define MAX_WAIT_MS 200
diff --git a/res/res_stasis_http_events.c b/res/res_stasis_http_events.c
index 3b2a9735f3ec4a2536dc8662fe6f33828fc8b7c1..7c6ed445f14381d1f824d7ea24b4302d430ab32c 100644
--- a/res/res_stasis_http_events.c
+++ b/res/res_stasis_http_events.c
@@ -44,7 +44,6 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
 #include "asterisk/module.h"
 #include "asterisk/stasis_app.h"
 #include "stasis_http/resource_events.h"
-#include "asterisk/stasis_channels.h"
 
 /*!
  * \brief Parameter parsing callback for /events.
@@ -79,524 +78,6 @@ static struct stasis_rest_handlers events = {
 	.children = {  }
 };
 
-struct ast_json *stasis_json_event_channel_snapshot_create(
-	struct ast_channel_snapshot *channel_snapshot
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-
-	event = ast_json_object_create();
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_snapshot", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_destroyed_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "cause");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	validator = ast_json_object_get(blob, "cause_txt");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_destroyed", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_caller_id_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "caller_presentation_txt");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	validator = ast_json_object_get(blob, "caller_presentation");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_caller_id", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_hangup_request_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "soft");
-	if (validator) {
-		/* do validation? XXX */
-	}
-
-	validator = ast_json_object_get(blob, "cause");
-	if (validator) {
-		/* do validation? XXX */
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_hangup_request", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_application_replaced_create(
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "application");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "application_replaced", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_varset_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "variable");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	validator = ast_json_object_get(blob, "value");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_varset", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_userevent_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "eventname");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_userevent", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_created_create(
-	struct ast_channel_snapshot *channel_snapshot
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-
-	event = ast_json_object_create();
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_created", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_stasis_start_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "args");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "stasis_start", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_dialplan_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "application");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	validator = ast_json_object_get(blob, "application_data");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_dialplan", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_state_change_create(
-	struct ast_channel_snapshot *channel_snapshot
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-
-	event = ast_json_object_create();
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_state_change", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_channel_dtmf_received_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	struct ast_json *validator;
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-	ast_assert(blob != NULL);
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-
-	validator = ast_json_object_get(blob, "digit");
-	if (validator) {
-		/* do validation? XXX */
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-	}
-
-	event = ast_json_deep_copy(blob);
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "channel_dtmf_received", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-struct ast_json *stasis_json_event_stasis_end_create(
-	struct ast_channel_snapshot *channel_snapshot
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-	int ret;
-
-	ast_assert(channel_snapshot != NULL);
-
-	event = ast_json_object_create();
-	if (!event) {
-		return NULL;
-	}
-
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-	message = ast_json_pack("{s: o}", "stasis_end", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
 static int load_module(void)
 {
 	stasis_app_ref();
diff --git a/res/res_stasis_json_asterisk.c b/res/res_stasis_json_asterisk.c
new file mode 100644
index 0000000000000000000000000000000000000000..8a9c9cd1649eaf4a70a90d97fb43fb3f0e147d6e
--- /dev/null
+++ b/res/res_stasis_json_asterisk.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Asterisk resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_asterisk.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Asterisk resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_asterisk.exports.in b/res/res_stasis_json_asterisk.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_asterisk.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_bridges.c b/res/res_stasis_json_bridges.c
new file mode 100644
index 0000000000000000000000000000000000000000..9b2aac3f150efccf3ab2aac8cd2c486945b09122
--- /dev/null
+++ b/res/res_stasis_json_bridges.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Bridge resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_bridges.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Bridge resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_bridges.exports.in b/res/res_stasis_json_bridges.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_bridges.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_channels.c b/res/res_stasis_json_channels.c
new file mode 100644
index 0000000000000000000000000000000000000000..54490f2f929ab8543c37157b8f902f81a97b6950
--- /dev/null
+++ b/res/res_stasis_json_channels.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Channel resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_channels.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Channel resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_channels.exports.in b/res/res_stasis_json_channels.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_channels.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_endpoints.c b/res/res_stasis_json_endpoints.c
new file mode 100644
index 0000000000000000000000000000000000000000..0c1e07f9f459d7aea4a77eb8fcc0436fd706bc04
--- /dev/null
+++ b/res/res_stasis_json_endpoints.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Endpoint resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_endpoints.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Endpoint resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_endpoints.exports.in b/res/res_stasis_json_endpoints.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_endpoints.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_events.c b/res/res_stasis_json_events.c
new file mode 100644
index 0000000000000000000000000000000000000000..f843310b62eb38b469b6f9ee0a276d8e3644b94d
--- /dev/null
+++ b/res/res_stasis_json_events.c
@@ -0,0 +1,580 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief WebSocket resource
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_events.h"
+#include "asterisk/stasis_channels.h"
+
+struct ast_json *stasis_json_event_channel_snapshot_create(
+	struct ast_channel_snapshot *channel_snapshot
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+
+	event = ast_json_object_create();
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_snapshot", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_destroyed_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "cause");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	validator = ast_json_object_get(blob, "cause_txt");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_destroyed", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_caller_id_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "caller_presentation_txt");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	validator = ast_json_object_get(blob, "caller_presentation");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_caller_id", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_hangup_request_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "soft");
+	if (validator) {
+		/* do validation? XXX */
+	}
+
+	validator = ast_json_object_get(blob, "cause");
+	if (validator) {
+		/* do validation? XXX */
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_hangup_request", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_application_replaced_create(
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "application");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "application_replaced", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_varset_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "variable");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	validator = ast_json_object_get(blob, "value");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_varset", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_userevent_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "eventname");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_userevent", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_created_create(
+	struct ast_channel_snapshot *channel_snapshot
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+
+	event = ast_json_object_create();
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_created", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_stasis_start_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "args");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "stasis_start", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_dialplan_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "application");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	validator = ast_json_object_get(blob, "application_data");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_dialplan", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_state_change_create(
+	struct ast_channel_snapshot *channel_snapshot
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+
+	event = ast_json_object_create();
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_state_change", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_channel_dtmf_received_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	struct ast_json *validator;
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+	ast_assert(blob != NULL);
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+
+	validator = ast_json_object_get(blob, "digit");
+	if (validator) {
+		/* do validation? XXX */
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+	}
+
+	event = ast_json_deep_copy(blob);
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "channel_dtmf_received", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+struct ast_json *stasis_json_event_stasis_end_create(
+	struct ast_channel_snapshot *channel_snapshot
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+	int ret;
+
+	ast_assert(channel_snapshot != NULL);
+
+	event = ast_json_object_create();
+	if (!event) {
+		return NULL;
+	}
+
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+	message = ast_json_pack("{s: o}", "stasis_end", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - WebSocket resource",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_events.exports.in b/res/res_stasis_json_events.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5a260a5f3a24c717c6b0b2aec75c85c214dc1736
--- /dev/null
+++ b/res/res_stasis_json_events.exports.in
@@ -0,0 +1,18 @@
+{
+	global:
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_snapshot_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_destroyed_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_caller_id_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_hangup_request_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_application_replaced_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_varset_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_userevent_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_created_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_stasis_start_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_dialplan_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_state_change_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_channel_dtmf_received_create;
+		LINKER_SYMBOL_PREFIXstasis_json_event_stasis_end_create;
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_playback.c b/res/res_stasis_json_playback.c
new file mode 100644
index 0000000000000000000000000000000000000000..9df75a6cf10751f1bfc3405b831d6d4728a14973
--- /dev/null
+++ b/res/res_stasis_json_playback.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Playback control resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_playback.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Playback control resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_playback.exports.in b/res/res_stasis_json_playback.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_playback.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_recordings.c b/res/res_stasis_json_recordings.c
new file mode 100644
index 0000000000000000000000000000000000000000..af9bef0e4ac7c0a73b5699b333f727b340983948
--- /dev/null
+++ b/res/res_stasis_json_recordings.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Recording resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_recordings.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Recording resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_recordings.exports.in b/res/res_stasis_json_recordings.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_recordings.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/res_stasis_json_sounds.c b/res/res_stasis_json_sounds.c
new file mode 100644
index 0000000000000000000000000000000000000000..6c22d03b6133b43f7633890803a4b7dc30ac791a
--- /dev/null
+++ b/res/res_stasis_json_sounds.c
@@ -0,0 +1,60 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief Sound resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_sounds.h"
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - Sound resources",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
diff --git a/res/res_stasis_json_sounds.exports.in b/res/res_stasis_json_sounds.exports.in
new file mode 100644
index 0000000000000000000000000000000000000000..5e767549c47d22e877c78bf7d7feac6d0744bddf
--- /dev/null
+++ b/res/res_stasis_json_sounds.exports.in
@@ -0,0 +1,4 @@
+{
+	local:
+		*;
+};
diff --git a/res/stasis_http/resource_asterisk.h b/res/stasis_http/resource_asterisk.h
index 846ca37bc0402f83a8702b8275e107746ab6372e..0d373ccb29e31e0cca3a565bf0992cda7b3fdebb 100644
--- a/res/stasis_http/resource_asterisk.h
+++ b/res/stasis_http/resource_asterisk.h
@@ -53,10 +53,4 @@ struct ast_get_asterisk_info_args {
  */
 void stasis_http_get_asterisk_info(struct ast_variable *headers, struct ast_get_asterisk_info_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * AsteriskInfo
- */
-
 #endif /* _ASTERISK_RESOURCE_ASTERISK_H */
diff --git a/res/stasis_http/resource_bridges.h b/res/stasis_http/resource_bridges.h
index 6ae9c31ee9f9186add037c5d1045de6924e8db4b..db6db205bb6c3048331905510bdc8e011f15c0f0 100644
--- a/res/stasis_http/resource_bridges.h
+++ b/res/stasis_http/resource_bridges.h
@@ -151,12 +151,4 @@ struct ast_record_bridge_args {
  */
 void stasis_http_record_bridge(struct ast_variable *headers, struct ast_record_bridge_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Bridge
- * - channels: List[string] (required)
- * - bridgeType: string (required)
- */
-
 #endif /* _ASTERISK_RESOURCE_BRIDGES_H */
diff --git a/res/stasis_http/resource_channels.h b/res/stasis_http/resource_channels.h
index 975901de5bdead180aa361636164a60b51b2de54..2c78589b7c58033a25edfff8c9048a63aaf83332 100644
--- a/res/stasis_http/resource_channels.h
+++ b/res/stasis_http/resource_channels.h
@@ -241,34 +241,4 @@ struct ast_record_channel_args {
  */
 void stasis_http_record_channel(struct ast_variable *headers, struct ast_record_channel_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Originated
- * DialplanCEP
- * - priority: long (required)
- * - exten: string (required)
- * - context: string (required)
- * Channel
- * - accountcode: string (required)
- * - linkedid: string (required)
- * - name: string (required)
- * - userfield: string (required)
- * - caller: CallerID (required)
- * - creationtime: Date (required)
- * - state: string (required)
- * - parkinglot: string (required)
- * - peeraccount: string (required)
- * - appl: string (required)
- * - connected: CallerID (required)
- * - uniqueid: string (required)
- * - hangupsource: string (required)
- * - dialplan: DialplanCEP (required)
- * - data: string (required)
- * CallerID
- * - name: string (required)
- * - number: string (required)
- * Dialed
- */
-
 #endif /* _ASTERISK_RESOURCE_CHANNELS_H */
diff --git a/res/stasis_http/resource_endpoints.h b/res/stasis_http/resource_endpoints.h
index a0262c064effb3e8bb9ed0206c55434cac7b7287..0379901d93fefaa134d8954d3f9dbbb134a60194 100644
--- a/res/stasis_http/resource_endpoints.h
+++ b/res/stasis_http/resource_endpoints.h
@@ -79,12 +79,4 @@ struct ast_get_endpoint_args {
  */
 void stasis_http_get_endpoint(struct ast_variable *headers, struct ast_get_endpoint_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Endpoint
- * - resource: string (required)
- * - technology: string (required)
- */
-
 #endif /* _ASTERISK_RESOURCE_ENDPOINTS_H */
diff --git a/res/stasis_http/resource_events.h b/res/stasis_http/resource_events.h
index 150939d22515bdb421e1086b3c844b5cceb3a210..0f58476df5f19499b4bf300c7fc8ad46e9fd1c0f 100644
--- a/res/stasis_http/resource_events.h
+++ b/res/stasis_http/resource_events.h
@@ -55,240 +55,4 @@ struct ast_event_websocket_args {
  */
 void stasis_http_event_websocket(struct ast_variable *headers, struct ast_event_websocket_args *args, struct stasis_http_response *response);
 
-struct ast_channel_snapshot;
-struct ast_bridge_snapshot;
-
-/*!
- * \brief Some part of channel state changed.
- *
- * \param channel The channel to be used to generate this event
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_snapshot_create(
-	struct ast_channel_snapshot *channel_snapshot
-	);
-
-/*!
- * \brief Notification that a channel has been destroyed.
- *
- * \param channel The channel to be used to generate this event
- * \param blob JSON blob containing the following parameters:
- * - cause: integer - Integer representation of the cause of the hangup (required)
- * - cause_txt: string - Text representation of the cause of the hangup (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_destroyed_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Channel changed Caller ID.
- *
- * \param channel The channel that changed Caller ID.
- * \param blob JSON blob containing the following parameters:
- * - caller_presentation_txt: string - The text representation of the Caller Presentation value. (required)
- * - caller_presentation: integer - The integer representation of the Caller Presentation value. (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_caller_id_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief A hangup was requested on the channel.
- *
- * \param channel The channel on which the hangup was requested.
- * \param blob JSON blob containing the following parameters:
- * - soft: boolean - Whether the hangup request was a soft hangup request.
- * - cause: integer - Integer representation of the cause of the hangup.
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_hangup_request_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Notification that another WebSocket has taken over for an application.
- *
- * \param blob JSON blob containing the following parameters:
- * - application: string  (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_application_replaced_create(
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Channel variable changed.
- *
- * \param channel The channel on which the variable was set.
- * \param blob JSON blob containing the following parameters:
- * - variable: string - The variable that changed. (required)
- * - value: string - The new value of the variable. (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_varset_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief User-generated event with additional user-defined fields in the object.
- *
- * \param channel The channel that signaled the user event.
- * \param blob JSON blob containing the following parameters:
- * - eventname: string - The name of the user event. (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_userevent_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Notification that a channel has been created.
- *
- * \param channel The channel to be used to generate this event
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_created_create(
-	struct ast_channel_snapshot *channel_snapshot
-	);
-
-/*!
- * \brief Notification that a channel has entered a Stasis appliction.
- *
- * \param channel The channel to be used to generate this event
- * \param blob JSON blob containing the following parameters:
- * - args: List[string] - Arguments to the application (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_stasis_start_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Channel changed location in the dialplan.
- *
- * \param channel The channel that changed dialplan location.
- * \param blob JSON blob containing the following parameters:
- * - application: string - The application that the channel is currently in. (required)
- * - application_data: string - The data that was passed to the application when it was invoked. (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_dialplan_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Notification of a channel's state change.
- *
- * \param channel The channel to be used to generate this event
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_state_change_create(
-	struct ast_channel_snapshot *channel_snapshot
-	);
-
-/*!
- * \brief DTMF received on a channel.
- *
- * \param channel The channel on which DTMF was received
- * \param blob JSON blob containing the following parameters:
- * - digit: string - DTMF digit received (0-9, A-E, # or *) (required)
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_channel_dtmf_received_create(
-	struct ast_channel_snapshot *channel_snapshot,
-	struct ast_json *blob
-	);
-
-/*!
- * \brief Notification that a channel has left a Stasis appliction.
- *
- * \param channel The channel to be used to generate this event
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-struct ast_json *stasis_json_event_stasis_end_create(
-	struct ast_channel_snapshot *channel_snapshot
-	);
-
-/*
- * JSON models
- *
- * ChannelSnapshot
- * ChannelDestroyed
- * - cause: integer (required)
- * - cause_txt: string (required)
- * ChannelCallerId
- * - caller_presentation_txt: string (required)
- * - caller_presentation: integer (required)
- * ChannelHangupRequest
- * - soft: boolean
- * - cause: integer
- * ApplicationReplaced
- * - application: string (required)
- * ChannelVarset
- * - variable: string (required)
- * - value: string (required)
- * ChannelUserevent
- * - eventname: string (required)
- * ChannelCreated
- * StasisStart
- * - args: List[string] (required)
- * ChannelDialplan
- * - application: string (required)
- * - application_data: string (required)
- * ChannelStateChange
- * ChannelDtmfReceived
- * - digit: string (required)
- * Event
- * - channel_created: ChannelCreated
- * - channel_destroyed: ChannelDestroyed
- * - channel_dialplan: ChannelDialplan
- * - channel_varset: ChannelVarset
- * - application_replaced: ApplicationReplaced
- * - channel_state_change: ChannelStateChange
- * - stasis_start: StasisStart
- * - application: string (required)
- * - channel_hangup_request: ChannelHangupRequest
- * - channel_userevent: ChannelUserevent
- * - channel_snapshot: ChannelSnapshot
- * - channel_dtmf_received: ChannelDtmfReceived
- * - channel_caller_id: ChannelCallerId
- * - stasis_end: StasisEnd
- * StasisEnd
- */
-
 #endif /* _ASTERISK_RESOURCE_EVENTS_H */
diff --git a/res/stasis_http/resource_playback.h b/res/stasis_http/resource_playback.h
index 9fb58e8e4ec9fccacfa0f01f1af0c877645bf1f7..36b05bc0497e7bf452bb71dc721d91478907dd82 100644
--- a/res/stasis_http/resource_playback.h
+++ b/res/stasis_http/resource_playback.h
@@ -81,11 +81,4 @@ struct ast_control_playback_args {
  */
 void stasis_http_control_playback(struct ast_variable *headers, struct ast_control_playback_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Playback
- * - id: string (required)
- */
-
 #endif /* _ASTERISK_RESOURCE_PLAYBACK_H */
diff --git a/res/stasis_http/resource_recordings.h b/res/stasis_http/resource_recordings.h
index d062da9961bfe97cc2ce2346463519c14ea36746..ee48e43b778054d4687e1f11de0f4a8add8a0af8 100644
--- a/res/stasis_http/resource_recordings.h
+++ b/res/stasis_http/resource_recordings.h
@@ -190,18 +190,4 @@ struct ast_unmute_recording_args {
  */
 void stasis_http_unmute_recording(struct ast_variable *headers, struct ast_unmute_recording_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Recording
- * - id: string (required)
- * StoredRecording
- * - durationSeconds: int
- * - time: Date
- * - id: string (required)
- * - formats: List[string] (required)
- * LiveRecording
- * - id: string (required)
- */
-
 #endif /* _ASTERISK_RESOURCE_RECORDINGS_H */
diff --git a/res/stasis_http/resource_sounds.h b/res/stasis_http/resource_sounds.h
index 9d724b35903fd0a741fbc394ef09b34ab9557e61..f3010a92010c001bf16c06b6b46e3a5bcace7dad 100644
--- a/res/stasis_http/resource_sounds.h
+++ b/res/stasis_http/resource_sounds.h
@@ -66,14 +66,4 @@ struct ast_get_stored_sound_args {
  */
 void stasis_http_get_stored_sound(struct ast_variable *headers, struct ast_get_stored_sound_args *args, struct stasis_http_response *response);
 
-/*
- * JSON models
- *
- * Sound
- * - lang: string (required)
- * - text: string
- * - id: string (required)
- * - formats: List[string] (required)
- */
-
 #endif /* _ASTERISK_RESOURCE_SOUNDS_H */
diff --git a/res/stasis_json/resource_asterisk.h b/res/stasis_json/resource_asterisk.h
new file mode 100644
index 0000000000000000000000000000000000000000..5a717d005bc3b1f3d042e1068f131c0c70182dad
--- /dev/null
+++ b/res/stasis_json/resource_asterisk.h
@@ -0,0 +1,46 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_asterisk.c
+ *
+ * Asterisk resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_ASTERISK_H
+#define _ASTERISK_RESOURCE_ASTERISK_H
+
+/*
+ * JSON models
+ *
+ * AsteriskInfo
+ */
+
+#endif /* _ASTERISK_RESOURCE_ASTERISK_H */
diff --git a/res/stasis_json/resource_bridges.h b/res/stasis_json/resource_bridges.h
new file mode 100644
index 0000000000000000000000000000000000000000..cf2d03dc7f346759e080c468ba116338fe3538f2
--- /dev/null
+++ b/res/stasis_json/resource_bridges.h
@@ -0,0 +1,48 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_bridges.c
+ *
+ * Bridge resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_BRIDGES_H
+#define _ASTERISK_RESOURCE_BRIDGES_H
+
+/*
+ * JSON models
+ *
+ * Bridge
+ * - channels: List[string] (required)
+ * - bridgeType: string (required)
+ */
+
+#endif /* _ASTERISK_RESOURCE_BRIDGES_H */
diff --git a/res/stasis_json/resource_channels.h b/res/stasis_json/resource_channels.h
new file mode 100644
index 0000000000000000000000000000000000000000..45e1031fc1c5e61a54d2a71312fa6ed49d642652
--- /dev/null
+++ b/res/stasis_json/resource_channels.h
@@ -0,0 +1,70 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_channels.c
+ *
+ * Channel resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_CHANNELS_H
+#define _ASTERISK_RESOURCE_CHANNELS_H
+
+/*
+ * JSON models
+ *
+ * Originated
+ * DialplanCEP
+ * - priority: long (required)
+ * - exten: string (required)
+ * - context: string (required)
+ * Channel
+ * - accountcode: string (required)
+ * - linkedid: string (required)
+ * - name: string (required)
+ * - userfield: string (required)
+ * - caller: CallerID (required)
+ * - creationtime: Date (required)
+ * - state: string (required)
+ * - parkinglot: string (required)
+ * - peeraccount: string (required)
+ * - appl: string (required)
+ * - connected: CallerID (required)
+ * - uniqueid: string (required)
+ * - hangupsource: string (required)
+ * - dialplan: DialplanCEP (required)
+ * - data: string (required)
+ * CallerID
+ * - name: string (required)
+ * - number: string (required)
+ * Dialed
+ */
+
+#endif /* _ASTERISK_RESOURCE_CHANNELS_H */
diff --git a/res/stasis_json/resource_endpoints.h b/res/stasis_json/resource_endpoints.h
new file mode 100644
index 0000000000000000000000000000000000000000..7f2e4233c5bef774e0e6d168a56c1af1b58f034c
--- /dev/null
+++ b/res/stasis_json/resource_endpoints.h
@@ -0,0 +1,48 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_endpoints.c
+ *
+ * Endpoint resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_ENDPOINTS_H
+#define _ASTERISK_RESOURCE_ENDPOINTS_H
+
+/*
+ * JSON models
+ *
+ * Endpoint
+ * - resource: string (required)
+ * - technology: string (required)
+ */
+
+#endif /* _ASTERISK_RESOURCE_ENDPOINTS_H */
diff --git a/res/stasis_json/resource_events.h b/res/stasis_json/resource_events.h
new file mode 100644
index 0000000000000000000000000000000000000000..bd1c3263b369b465cdea7f3f3d7e16793b4af727
--- /dev/null
+++ b/res/stasis_json/resource_events.h
@@ -0,0 +1,275 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_events.c
+ *
+ * WebSocket resource
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_EVENTS_H
+#define _ASTERISK_RESOURCE_EVENTS_H
+
+struct ast_channel_snapshot;
+
+/*!
+ * \brief Some part of channel state changed.
+ *
+ * \param channel The channel to be used to generate this event
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_snapshot_create(
+	struct ast_channel_snapshot *channel_snapshot
+	);
+
+/*!
+ * \brief Notification that a channel has been destroyed.
+ *
+ * \param channel The channel to be used to generate this event
+ * \param blob JSON blob containing the following parameters:
+ * - cause: integer - Integer representation of the cause of the hangup (required)
+ * - cause_txt: string - Text representation of the cause of the hangup (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_destroyed_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Channel changed Caller ID.
+ *
+ * \param channel The channel that changed Caller ID.
+ * \param blob JSON blob containing the following parameters:
+ * - caller_presentation_txt: string - The text representation of the Caller Presentation value. (required)
+ * - caller_presentation: integer - The integer representation of the Caller Presentation value. (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_caller_id_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief A hangup was requested on the channel.
+ *
+ * \param channel The channel on which the hangup was requested.
+ * \param blob JSON blob containing the following parameters:
+ * - soft: boolean - Whether the hangup request was a soft hangup request.
+ * - cause: integer - Integer representation of the cause of the hangup.
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_hangup_request_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Notification that another WebSocket has taken over for an application.
+ *
+ * \param blob JSON blob containing the following parameters:
+ * - application: string  (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_application_replaced_create(
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Channel variable changed.
+ *
+ * \param channel The channel on which the variable was set.
+ * \param blob JSON blob containing the following parameters:
+ * - variable: string - The variable that changed. (required)
+ * - value: string - The new value of the variable. (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_varset_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief User-generated event with additional user-defined fields in the object.
+ *
+ * \param channel The channel that signaled the user event.
+ * \param blob JSON blob containing the following parameters:
+ * - eventname: string - The name of the user event. (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_userevent_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Notification that a channel has been created.
+ *
+ * \param channel The channel to be used to generate this event
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_created_create(
+	struct ast_channel_snapshot *channel_snapshot
+	);
+
+/*!
+ * \brief Notification that a channel has entered a Stasis appliction.
+ *
+ * \param channel The channel to be used to generate this event
+ * \param blob JSON blob containing the following parameters:
+ * - args: List[string] - Arguments to the application (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_stasis_start_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Channel changed location in the dialplan.
+ *
+ * \param channel The channel that changed dialplan location.
+ * \param blob JSON blob containing the following parameters:
+ * - application: string - The application that the channel is currently in. (required)
+ * - application_data: string - The data that was passed to the application when it was invoked. (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_dialplan_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Notification of a channel's state change.
+ *
+ * \param channel The channel to be used to generate this event
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_state_change_create(
+	struct ast_channel_snapshot *channel_snapshot
+	);
+
+/*!
+ * \brief DTMF received on a channel.
+ *
+ * \param channel The channel on which DTMF was received
+ * \param blob JSON blob containing the following parameters:
+ * - digit: string - DTMF digit received (0-9, A-E, # or *) (required)
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_channel_dtmf_received_create(
+	struct ast_channel_snapshot *channel_snapshot,
+	struct ast_json *blob
+	);
+
+/*!
+ * \brief Notification that a channel has left a Stasis appliction.
+ *
+ * \param channel The channel to be used to generate this event
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+struct ast_json *stasis_json_event_stasis_end_create(
+	struct ast_channel_snapshot *channel_snapshot
+	);
+
+/*
+ * JSON models
+ *
+ * ChannelSnapshot
+ * ChannelDestroyed
+ * - cause: integer (required)
+ * - cause_txt: string (required)
+ * ChannelCallerId
+ * - caller_presentation_txt: string (required)
+ * - caller_presentation: integer (required)
+ * ChannelHangupRequest
+ * - soft: boolean
+ * - cause: integer
+ * ApplicationReplaced
+ * - application: string (required)
+ * ChannelVarset
+ * - variable: string (required)
+ * - value: string (required)
+ * ChannelUserevent
+ * - eventname: string (required)
+ * ChannelCreated
+ * StasisStart
+ * - args: List[string] (required)
+ * ChannelDialplan
+ * - application: string (required)
+ * - application_data: string (required)
+ * ChannelStateChange
+ * ChannelDtmfReceived
+ * - digit: string (required)
+ * Event
+ * - channel_created: ChannelCreated
+ * - channel_destroyed: ChannelDestroyed
+ * - channel_dialplan: ChannelDialplan
+ * - channel_varset: ChannelVarset
+ * - application_replaced: ApplicationReplaced
+ * - channel_state_change: ChannelStateChange
+ * - stasis_start: StasisStart
+ * - application: string (required)
+ * - channel_hangup_request: ChannelHangupRequest
+ * - channel_userevent: ChannelUserevent
+ * - channel_snapshot: ChannelSnapshot
+ * - channel_dtmf_received: ChannelDtmfReceived
+ * - channel_caller_id: ChannelCallerId
+ * - stasis_end: StasisEnd
+ * StasisEnd
+ */
+
+#endif /* _ASTERISK_RESOURCE_EVENTS_H */
diff --git a/res/stasis_json/resource_playback.h b/res/stasis_json/resource_playback.h
new file mode 100644
index 0000000000000000000000000000000000000000..e84e6de0dfa1f202b9d64153cdbee650dcd0458e
--- /dev/null
+++ b/res/stasis_json/resource_playback.h
@@ -0,0 +1,47 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_playback.c
+ *
+ * Playback control resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_PLAYBACK_H
+#define _ASTERISK_RESOURCE_PLAYBACK_H
+
+/*
+ * JSON models
+ *
+ * Playback
+ * - id: string (required)
+ */
+
+#endif /* _ASTERISK_RESOURCE_PLAYBACK_H */
diff --git a/res/stasis_json/resource_recordings.h b/res/stasis_json/resource_recordings.h
new file mode 100644
index 0000000000000000000000000000000000000000..b460fb7696527959f8b95303a857cf9f2db1f965
--- /dev/null
+++ b/res/stasis_json/resource_recordings.h
@@ -0,0 +1,54 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_recordings.c
+ *
+ * Recording resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_RECORDINGS_H
+#define _ASTERISK_RESOURCE_RECORDINGS_H
+
+/*
+ * JSON models
+ *
+ * Recording
+ * - id: string (required)
+ * StoredRecording
+ * - durationSeconds: int
+ * - time: Date
+ * - id: string (required)
+ * - formats: List[string] (required)
+ * LiveRecording
+ * - id: string (required)
+ */
+
+#endif /* _ASTERISK_RESOURCE_RECORDINGS_H */
diff --git a/res/stasis_json/resource_sounds.h b/res/stasis_json/resource_sounds.h
new file mode 100644
index 0000000000000000000000000000000000000000..306e2e4a8f8c17ec8722e44eff5edd42e7748a67
--- /dev/null
+++ b/res/stasis_json/resource_sounds.h
@@ -0,0 +1,50 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2012 - 2013, Digium, Inc.
+ *
+ * David M. Lee, II <dlee@digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_sounds.c
+ *
+ * Sound resources
+ *
+ * \author David M. Lee, II <dlee@digium.com>
+ */
+
+/*
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * !!!!!                               DO NOT EDIT                        !!!!!
+ * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_SOUNDS_H
+#define _ASTERISK_RESOURCE_SOUNDS_H
+
+/*
+ * JSON models
+ *
+ * Sound
+ * - lang: string (required)
+ * - text: string
+ * - id: string (required)
+ * - formats: List[string] (required)
+ */
+
+#endif /* _ASTERISK_RESOURCE_SOUNDS_H */
diff --git a/rest-api-templates/make_stasis_http_stubs.py b/rest-api-templates/make_stasis_http_stubs.py
index 1ec7c5c91ac2bf5691a2070bdf559d768cf8e4a0..1114ea46e179c3f3147c221ea5fb9601cd917eb5 100755
--- a/rest-api-templates/make_stasis_http_stubs.py
+++ b/rest-api-templates/make_stasis_http_stubs.py
@@ -47,6 +47,12 @@ API_TRANSFORMS = [
               'stasis_http/resource_{{name}}.h'),
     Transform(rel('stasis_http_resource.c.mustache'),
               'stasis_http/resource_{{name}}.c', False),
+    Transform(rel('res_stasis_json_resource.c.mustache'),
+              'res_stasis_json_{{name}}.c'),
+    Transform(rel('res_stasis_json_resource.exports.mustache'),
+              'res_stasis_json_{{name}}.exports.in'),
+    Transform(rel('stasis_json_resource.h.mustache'),
+              'stasis_json/resource_{{name}}.h'),
 ]
 
 RESOURCES_TRANSFORMS = [
diff --git a/rest-api-templates/res_stasis_http_resource.c.mustache b/rest-api-templates/res_stasis_http_resource.c.mustache
index a9428c0607d7ffd041e6dffb4862e7d49a23ee6f..cf2876c0c5940b68ecdba9294ae2683b089000ca 100644
--- a/rest-api-templates/res_stasis_http_resource.c.mustache
+++ b/rest-api-templates/res_stasis_http_resource.c.mustache
@@ -49,9 +49,6 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
 #include "asterisk/module.h"
 #include "asterisk/stasis_app.h"
 #include "stasis_http/resource_{{name}}.h"
-{{#has_events}}
-#include "asterisk/stasis_channels.h"
-{{/has_events}}
 
 {{#apis}}
 {{#operations}}
@@ -101,89 +98,6 @@ static void stasis_http_{{c_nickname}}_cb(
 {{> rest_handler}}
 {{/root_path}}
 
-{{#has_events}}
-{{#events}}
-{{> event_function_decl}}
-	)
-{
-	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
-	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
-{{#has_properties}}
-	struct ast_json *validator;
-{{/has_properties}}
-{{#channel}}
-	int ret;
-{{/channel}}
-{{#bridge}}
-{{^channel}}
-	int ret;
-{{/channel}}
-{{/bridge}}
-
-{{#channel}}
-	ast_assert(channel_snapshot != NULL);
-{{/channel}}
-{{#bridge}}
-	ast_assert(bridge_snapshot != NULL);
-{{/bridge}}
-{{#has_properties}}
-	ast_assert(blob != NULL);
-{{#channel}}
-	ast_assert(ast_json_object_get(blob, "channel") == NULL);
-{{/channel}}
-{{#bridge}}
-	ast_assert(ast_json_object_get(blob, "bridge") == NULL);
-{{/bridge}}
-	ast_assert(ast_json_object_get(blob, "type") == NULL);
-{{#properties}}
-
-	validator = ast_json_object_get(blob, "{{name}}");
-	if (validator) {
-		/* do validation? XXX */
-{{#required}}
-	} else {
-		/* fail message generation if the required parameter doesn't exist */
-		return NULL;
-{{/required}}
-	}
-{{/properties}}
-
-	event = ast_json_deep_copy(blob);
-{{/has_properties}}
-{{^has_properties}}
-
-	event = ast_json_object_create();
-{{/has_properties}}
-	if (!event) {
-		return NULL;
-	}
-
-{{#channel}}
-	ret = ast_json_object_set(event,
-		"channel", ast_channel_snapshot_to_json(channel_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-{{/channel}}
-{{#bridge}}
-	ret = ast_json_object_set(event,
-		"bridge", ast_bridge_snapshot_to_json(bridge_snapshot));
-	if (ret) {
-		return NULL;
-	}
-
-{{/bridge}}
-	message = ast_json_pack("{s: o}", "{{c_id}}", ast_json_ref(event));
-	if (!message) {
-		return NULL;
-	}
-
-	return ast_json_ref(message);
-}
-
-{{/events}}
-{{/has_events}}
 static int load_module(void)
 {
 	stasis_app_ref();
diff --git a/rest-api-templates/res_stasis_json_resource.c.mustache b/rest-api-templates/res_stasis_json_resource.c.mustache
new file mode 100644
index 0000000000000000000000000000000000000000..0398302702371d400237e835f230fdf65be3fe3c
--- /dev/null
+++ b/rest-api-templates/res_stasis_json_resource.c.mustache
@@ -0,0 +1,151 @@
+{{#api_declaration}}
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * {{{copyright}}}
+ *
+ * {{{author}}}
+{{! Template Copyright
+ * Copyright (C) 2013, Digium, Inc.
+ *
+ * Kinsey Moore <kmoore@digium.com>
+}}
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+{{! Template for rendering the res_ module for an HTTP resource. }}
+/*
+{{> do-not-edit}}
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/res_stasis_http_resource.c.mustache
+ */
+
+/*! \file
+ *
+ * \brief {{{description}}}
+ *
+ * \author {{{author}}}
+ */
+
+/*** MODULEINFO
+	<support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
+
+#include "asterisk/module.h"
+#include "asterisk/json.h"
+#include "stasis_json/resource_{{name}}.h"
+{{#has_events}}
+#include "asterisk/stasis_channels.h"
+
+{{#events}}
+{{> event_function_decl}}
+	)
+{
+	RAII_VAR(struct ast_json *, message, NULL, ast_json_unref);
+	RAII_VAR(struct ast_json *, event, NULL, ast_json_unref);
+{{#has_properties}}
+	struct ast_json *validator;
+{{/has_properties}}
+{{#channel}}
+	int ret;
+{{/channel}}
+{{#bridge}}
+{{^channel}}
+	int ret;
+{{/channel}}
+{{/bridge}}
+
+{{#channel}}
+	ast_assert(channel_snapshot != NULL);
+{{/channel}}
+{{#bridge}}
+	ast_assert(bridge_snapshot != NULL);
+{{/bridge}}
+{{#has_properties}}
+	ast_assert(blob != NULL);
+{{#channel}}
+	ast_assert(ast_json_object_get(blob, "channel") == NULL);
+{{/channel}}
+{{#bridge}}
+	ast_assert(ast_json_object_get(blob, "bridge") == NULL);
+{{/bridge}}
+	ast_assert(ast_json_object_get(blob, "type") == NULL);
+{{#properties}}
+
+	validator = ast_json_object_get(blob, "{{name}}");
+	if (validator) {
+		/* do validation? XXX */
+{{#required}}
+	} else {
+		/* fail message generation if the required parameter doesn't exist */
+		return NULL;
+{{/required}}
+	}
+{{/properties}}
+
+	event = ast_json_deep_copy(blob);
+{{/has_properties}}
+{{^has_properties}}
+
+	event = ast_json_object_create();
+{{/has_properties}}
+	if (!event) {
+		return NULL;
+	}
+
+{{#channel}}
+	ret = ast_json_object_set(event,
+		"channel", ast_channel_snapshot_to_json(channel_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+{{/channel}}
+{{#bridge}}
+	ret = ast_json_object_set(event,
+		"bridge", ast_bridge_snapshot_to_json(bridge_snapshot));
+	if (ret) {
+		return NULL;
+	}
+
+{{/bridge}}
+	message = ast_json_pack("{s: o}", "{{c_id}}", ast_json_ref(event));
+	if (!message) {
+		return NULL;
+	}
+
+	return ast_json_ref(message);
+}
+
+{{/events}}
+{{/has_events}}
+static int load_module(void)
+{
+	return 0;
+}
+
+static int unload_module(void)
+{
+	return 0;
+}
+
+AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS | AST_MODFLAG_LOAD_ORDER,
+	"Stasis JSON Generators and Validators - {{{description}}}",
+	.load = load_module,
+	.unload = unload_module,
+	.load_pri = AST_MODPRI_DEFAULT,
+	);
+{{/api_declaration}}
diff --git a/rest-api-templates/res_stasis_json_resource.exports.mustache b/rest-api-templates/res_stasis_json_resource.exports.mustache
new file mode 100644
index 0000000000000000000000000000000000000000..0f958fa04890c3f4a9ba4c382208fe03dcce7f8e
--- /dev/null
+++ b/rest-api-templates/res_stasis_json_resource.exports.mustache
@@ -0,0 +1,12 @@
+{
+{{#api_declaration}}
+{{#has_events}}
+	global:
+{{#events}}
+		LINKER_SYMBOL_PREFIXstasis_json_event_{{c_id}}_create;
+{{/events}}
+{{/has_events}}
+{{/api_declaration}}
+	local:
+		*;
+};
diff --git a/rest-api-templates/stasis_http_resource.h.mustache b/rest-api-templates/stasis_http_resource.h.mustache
index 2a417186cb25a8b9f12c81aeb76b8aa9287ea383..6e7af1648ff2143f5875be605286d41396d77002 100644
--- a/rest-api-templates/stasis_http_resource.h.mustache
+++ b/rest-api-templates/stasis_http_resource.h.mustache
@@ -64,48 +64,5 @@ void stasis_http_{{c_nickname}}(struct ast_variable *headers, struct ast_{{c_nic
 {{/operations}}
 {{/apis}}
 
-{{#has_events}}
-struct ast_channel_snapshot;
-struct ast_bridge_snapshot;
-
-{{#events}}
-/*!
- * \brief {{description}}
-{{#notes}}
- *
- * {{{notes}}}
-{{/notes}}
- *
-{{#channel}}
- * \param channel {{#channel_desc}}{{channel_desc}}{{/channel_desc}}{{^channel_desc}}The channel to be used to generate this event{{/channel_desc}}
-{{/channel}}
-{{#bridge}}
- * \param bridge {{#bridge_desc}}{{bridge_desc}}{{/bridge_desc}}{{^bridge_desc}}The bridge to be used to generate this event{{/bridge_desc}}
-{{/bridge}}
-{{#has_properties}}
- * \param blob JSON blob containing the following parameters:
-{{/has_properties}}
-{{#properties}}
- * - {{name}}: {{type}} {{#description}}- {{description}}{{/description}}{{#required}} (required){{/required}}
-{{/properties}}
- *
- * \retval NULL on error
- * \retval JSON (ast_json) describing the event
- */
-{{> event_function_decl}}
-	);
-
-{{/events}}
-{{/has_events}}
-/*
- * JSON models
- *
-{{#models}}
- * {{id}}
-{{#properties}}
- * - {{name}}: {{type}}{{#required}} (required){{/required}}
-{{/properties}}
-{{/models}} */
-
 #endif /* _ASTERISK_RESOURCE_{{name_caps}}_H */
 {{/api_declaration}}
diff --git a/rest-api-templates/stasis_json_resource.h.mustache b/rest-api-templates/stasis_json_resource.h.mustache
new file mode 100644
index 0000000000000000000000000000000000000000..f55e830bda0c1a416ae037f3b6ce66b08a0b9eb8
--- /dev/null
+++ b/rest-api-templates/stasis_json_resource.h.mustache
@@ -0,0 +1,82 @@
+{{#api_declaration}}
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * {{{copyright}}}
+ *
+ * {{{author}}}
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*! \file
+ *
+ * \brief Generated file - declares stubs to be implemented in
+ * res/stasis_json/resource_{{name}}.c
+ *
+ * {{{description}}}
+ *
+ * \author {{{author}}}
+ */
+
+/*
+{{> do-not-edit}}
+ * This file is generated by a mustache template. Please see the original
+ * template in rest-api-templates/stasis_http_resource.h.mustache
+ */
+
+#ifndef _ASTERISK_RESOURCE_{{name_caps}}_H
+#define _ASTERISK_RESOURCE_{{name_caps}}_H
+
+{{#has_events}}
+struct ast_channel_snapshot;
+
+{{#events}}
+/*!
+ * \brief {{description}}
+{{#notes}}
+ *
+ * {{{notes}}}
+{{/notes}}
+ *
+{{#channel}}
+ * \param channel {{#channel_desc}}{{channel_desc}}{{/channel_desc}}{{^channel_desc}}The channel to be used to generate this event{{/channel_desc}}
+{{/channel}}
+{{#bridge}}
+ * \param bridge {{#bridge_desc}}{{bridge_desc}}{{/bridge_desc}}{{^bridge_desc}}The bridge to be used to generate this event{{/bridge_desc}}
+{{/bridge}}
+{{#has_properties}}
+ * \param blob JSON blob containing the following parameters:
+{{/has_properties}}
+{{#properties}}
+ * - {{name}}: {{type}} {{#description}}- {{description}}{{/description}}{{#required}} (required){{/required}}
+{{/properties}}
+ *
+ * \retval NULL on error
+ * \retval JSON (ast_json) describing the event
+ */
+{{> event_function_decl}}
+	);
+
+{{/events}}
+{{/has_events}}
+/*
+ * JSON models
+ *
+{{#models}}
+ * {{id}}
+{{#properties}}
+ * - {{name}}: {{type}}{{#required}} (required){{/required}}
+{{/properties}}
+{{/models}} */
+
+#endif /* _ASTERISK_RESOURCE_{{name_caps}}_H */
+{{/api_declaration}}
diff --git a/tests/test_res_stasis.c b/tests/test_res_stasis.c
index a824b8a8daa7b7e96f1e35cf9dc0cbbfd9e47aea..321f40f3d59b1015ae968aab2c6aac680243eee1 100644
--- a/tests/test_res_stasis.c
+++ b/tests/test_res_stasis.c
@@ -157,7 +157,7 @@ AST_TEST_DEFINE(app_replaced)
 
 	stasis_app_register(app_name, test_handler, app_data1);
 	stasis_app_register(app_name, test_handler, app_data2);
-	expected_message1 = ast_json_pack("[{s: {}}]", "application-replaced");
+	expected_message1 = ast_json_pack("[{s: {s: s}}]", "application_replaced", "application", app_name);
 	message = ast_json_pack("{ s: o }", "test-message", ast_json_null());
 	expected_message2 = ast_json_pack("[o]", ast_json_ref(message));