diff options
author | Peter Volkov <pva@gentoo.org> | 2010-01-18 21:02:26 +0000 |
---|---|---|
committer | Peter Volkov <pva@gentoo.org> | 2010-01-18 21:02:26 +0000 |
commit | 3c94ddb0f1d74227142919b09abcf060420b8b74 (patch) | |
tree | 369273756a3e56fdbe8d5af7f7aebcc9d5c7d469 | |
parent | net-firewall/xtables-addons: Version bump. (diff) | |
download | pva-3c94ddb0f1d74227142919b09abcf060420b8b74.tar.gz pva-3c94ddb0f1d74227142919b09abcf060420b8b74.tar.bz2 pva-3c94ddb0f1d74227142919b09abcf060420b8b74.zip |
net-im/ejabberd: Version bump, bug #281366.
svn path=/; revision=373
-rw-r--r-- | net-im/ejabberd/ChangeLog | 224 | ||||
-rw-r--r-- | net-im/ejabberd/Manifest | 18 | ||||
-rw-r--r-- | net-im/ejabberd/ejabberd-2.1.2.ebuild | 163 | ||||
-rw-r--r-- | net-im/ejabberd/files/2.1.0-mod_statsdx.patch | 1895 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberd-2.confd | 23 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberd-2.initd | 54 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberd-wrapper-2.template | 49 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberd-wrapper-3.template | 50 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberd-wrapper.template | 49 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberdctl | 8 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberdctl-wrapper-2.template | 30 | ||||
-rw-r--r-- | net-im/ejabberd/files/ejabberdctl-wrapper-3.template | 46 | ||||
-rw-r--r-- | net-im/ejabberd/files/inetrc | 1 | ||||
-rw-r--r-- | net-im/ejabberd/files/self-cert-v2.sh | 41 | ||||
-rw-r--r-- | net-im/ejabberd/files/self-cert-v3.sh | 128 | ||||
-rw-r--r-- | net-im/ejabberd/files/self-cert.sh | 21 | ||||
-rw-r--r-- | net-im/ejabberd/files/ssl.cnf | 36 | ||||
-rw-r--r-- | net-im/ejabberd/metadata.xml | 20 |
18 files changed, 2856 insertions, 0 deletions
diff --git a/net-im/ejabberd/ChangeLog b/net-im/ejabberd/ChangeLog new file mode 100644 index 0000000..663d7ec --- /dev/null +++ b/net-im/ejabberd/ChangeLog @@ -0,0 +1,224 @@ +# ChangeLog for net-im/ejabberd +# Copyright 1999-2008 Gentoo Foundation; Distributed under the GPL v2 +# $Header: /var/cvsroot/gentoo-x86/net-im/ejabberd/ChangeLog,v 1.42 2008/07/19 12:22:53 caleb Exp $ + +*ejabberd-2.0.1_p2-r1 (19 Jul 2008) + + 19 Jul 2008; Caleb Tennis <caleb@gentoo.org> + +files/2.0.1-parallel-make.patch, +ejabberd-2.0.1_p2-r1.ebuild: + Add parallel make patch per 225565 + + 19 Jul 2008; Caleb Tennis <caleb@gentoo.org> ejabberd-2.0.1_p2.ebuild: + amd64 stable per #231676 + + 25 May 2008; Caleb Tennis <caleb@gentoo.org> ejabberd-2.0.1_p2.ebuild: + make /var/lib/ejabberd directory + + 23 May 2008; Caleb Tennis <caleb@gentoo.org> ejabberd-2.0.1_p2.ebuild: + add pam use flag and set permissions on pam helper + +*ejabberd-2.0.1_p2 (23 May 2008) + + 23 May 2008; Caleb Tennis <caleb@gentoo.org> -ejabberd-2.0.1.ebuild, + +ejabberd-2.0.1_p2.ebuild: + bump to a new upstream version + + 22 May 2008; Caleb Tennis <caleb@gentoo.org> files/ejabberd-2.0.1.initd, + +files/ejabberd-wrapper-2.0.1.template, + +files/ejabberdctl-wrapper-2.0.1.template, ejabberd-2.0.1.ebuild: + add some fixes from 207586 + +*ejabberd-2.0.1 (22 May 2008) + + 22 May 2008; Caleb Tennis <caleb@gentoo.org> files/ejabberd-2.0.0.initd, + +ejabberd-2.0.1.ebuild: + version bump + + 13 Apr 2008; Caleb Tennis <caleb@gentoo.org> files/self-cert-v2.sh, + ejabberd-2.0.0-r1.ebuild: + Update self-cert-v2.sh + + 13 Apr 2008; Caleb Tennis <caleb@gentoo.org> ejabberd-2.0.0-r1.ebuild: + Fix homepage + +*ejabberd-2.0.0-r1 (13 Apr 2008) + + 13 Apr 2008; Caleb Tennis <caleb@gentoo.org> +files/ejabberd-2.0.0.confd, + files/ejabberd-2.0.0.initd, +files/ejabberd-wrapper-2.0.0.template, + +files/ejabberdctl-wrapper-2.0.0.template, + +files/2.0.0-ejab-542-mod_proxy65.patch, + +files/2.0.0-erlang12-s2s-in.patch, -ejabberd-2.0.0.ebuild, + +ejabberd-2.0.0-r1.ebuild: + Bump revision with a whole new ebuild, thanks to the folks in bug #207586 + + 17 Mar 2008; Tony Vroon <chainsaw@gentoo.org> metadata.xml: + Mark caleb as maintainer of this package. + + 22 Feb 2008; Caleb Tennis <caleb@gentoo.org> +files/ejabberd-1.1.4.confd, + ejabberd-1.1.4.ebuild, ejabberd-1.1.4-r1.ebuild: + 1.1.4 was using the 1.1.3 conf file, so create a 1.1.4 conf file and update + the ebuilds to use it + +*ejabberd-2.0.0 (22 Feb 2008) + + 22 Feb 2008; Caleb Tennis <caleb@gentoo.org> -files/ejabberd-1.1.3.confd, + -files/1.1.3-missing-declaration.patch, -ejabberd-1.1.3.ebuild, + -ejabberd-1.1.3-r1.ebuild, -ejabberd-1.1.3-r2.ebuild, + -ejabberd-2.0.0_rc1.ebuild, +ejabberd-2.0.0.ebuild: + bump to 2.0.0, remove old versions + + 10 Feb 2008; Luca Barbato <lu_zero@gentoo.org> ejabberd-2.0.0_rc1.ebuild: + Marked ~ppc + +*ejabberd-2.0.0_rc1 (05 Feb 2008) + + 05 Feb 2008; Caleb Tennis <caleb@gentoo.org> +files/ejabberd-2.0.0.initd, + +files/2.0.0-missing-declaration.patch, +ejabberd-2.0.0_rc1.ebuild: + Version bump, from bug #207586 + + 31 Jan 2008; Christian Faulhammer <opfer@gentoo.org> + ejabberd-1.1.4-r1.ebuild: + emergency stable x86 + +*ejabberd-1.1.4-r1 (11 Jan 2008) + + 11 Jan 2008; Christian Faulhammer <opfer@gentoo.org> + +files/ejabberd-1.1.4-erlang-12.patch, +ejabberd-1.1.4-r1.ebuild: + make ejabberd compile with Erlang 12B, patch take from Debian, reported in + bug 202114 by Conrad Kostecki <ConiKost AT gmx DOT de>, thanks to Anton + Romanov <theli AT ukr DOT net> + + 08 Dec 2007; Ulrich Mueller <ulm@gentoo.org> + +files/ejabberd-1.1.1-r1.initd, +files/ejabberd-1.1.1.confd: + Restore initd and confd files that are still needed. + + 08 Dec 2007; Tony Vroon <chainsaw@gentoo.org> -files/ejabberd-0.7.5.confd, + -files/ejabberd-0.7.5.initd, -files/ejabberd-1.1.1-r1.initd, + -files/ejabberd-1.1.1.confd, -files/ejabberd-1.1.1.initd, + -ejabberd-0.7.5.ebuild, -ejabberd-1.1.1.ebuild, -ejabberd-1.1.1-r1.ebuild, + -ejabberd-1.1.2-r1.ebuild: + Remove old ebuilds, including 1.1.1 which used an insecure docert statement + (per suggestion of Ulrich Mueller <ulm@gentoo.org> on IRC). Closes bug + #201677. + +*ejabberd-1.1.4 (14 Sep 2007) + + 14 Sep 2007; Tony Vroon <chainsaw@gentoo.org> +files/ejabberd-1.1.4.initd, + +files/1.1.4-missing-declaration.patch, +ejabberd-1.1.4.ebuild: + Version bump, closes bugs #188679, #192012 and #190266. + + 01 Sep 2007; Christian Faulhammer <opfer@gentoo.org> + ejabberd-1.1.3-r2.ebuild: + add a space that got lost in my previous change, reported by OlegON + <olegon.mail@gmail.com> in bug 190944 + + 29 Aug 2007; Christian Faulhammer <opfer@gentoo.org> + ejabberd-1.1.3-r2.ebuild: + remove restriction on lower erlang versions, see bug 184419; added some + quotes around variables + +*ejabberd-1.1.3-r2 (13 Jul 2007) + + 13 Jul 2007; Tony Vroon <chainsaw@gentoo.org> +ejabberd-1.1.3-r2.ebuild: + Debugging support by Justin <justin-gentoo@openaether.org>, closes bug + #174734. Do not attempt to automatically generate a key, this ends up being + interactive on some systems. Closes bug #178615 by Robin Johnson + <robbat2@gentoo.org>. Revert defective change from bug #161252, without + sname the daemon can not be stopped. Thanks to Conrad Kostecki + <ConiKost@gmx.de>, closes bug #181745. Restrict erlang dep to <11.2.5 to + avoid EOF during handshake, as reported by Santiago Gala <sgala@apache.org>, + closes bug #184419. Restrict openssl dep to >=0.9.8e so a messy die on + USE="zlib" in openssl is no longer required. Also a report by Conrad + Kostecki <ConiKost@gmx.de>, this closes bug #185009. + + 28 Apr 2007; Sven Wegener <swegener@gentoo.org> ejabberd-0.7.5.ebuild: + Fix *initd, *confd and *envd calls (#173884, #174266) + + 21 Apr 2007; Tony Vroon <chainsaw@gentoo.org> ejabberd-0.7.5.ebuild: + Stop using insinto /etc/conf.d and use the newconfd function instead, bug + #174266. + +*ejabberd-1.1.3-r1 (11 Apr 2007) + + 11 Apr 2007; Tony Vroon <chainsaw@gentoo.org> +files/ejabberd-1.1.3.confd, + +files/1.1.3-missing-declaration.patch, +ejabberd-1.1.3-r1.ebuild: + Revision bump, closes bugs #161252, #171427 and #171551. + + 11 Mar 2007; Markus Rothe <corsair@gentoo.org> ejabberd-1.1.3.ebuild: + Adding ~amd64 to 1.1.3, too. + + 11 Mar 2007; Peter Weller <welp@gentoo.org> ejabberd-1.1.2-r1.ebuild: + Keyworded ~amd64 wrt bug 141302 + + 28 Feb 2007; Christian Faulhammer <opfer@gentoo.org> + files/ejabberd-1.1.1-r1.initd, ejabberd-1.1.3.ebuild: + corrected init file; removed dodoc entry; stable x86; security bug 159580 + +*ejabberd-1.1.3 (27 Feb 2007) + + 27 Feb 2007; Stefan Cornelius <dercorny@gentoo.org> +ejabberd-1.1.3.ebuild: + Bumping to version 1.1.3 wrt security bug #159580 + + 27 Feb 2007; Gustavo Felisberto <humpback@gentoo.org>; metadata.xml: + Corrected maintainer in metadata. + + 22 Feb 2007; Piotr Jaroszyński <peper@gentoo.org> ChangeLog: + Transition to Manifest2. + +*ejabberd-1.1.2-r1 (16 Oct 2006) + + 16 Oct 2006; Tony Vroon <chainsaw@gentoo.org> -ejabberd-1.1.2.ebuild, + +ejabberd-1.1.2-r1.ebuild: + Pull set of utterly broken and apparently completely untested patches, bug + #137724 now closed as WONTFIX. + +*ejabberd-1.1.2 (13 Oct 2006) + + 13 Oct 2006; Tony Vroon <chainsaw@gentoo.org> +ejabberd-1.1.2.ebuild: + New upstream version. Patchball updated with mod_presence, all thanks to + Nikolaus Polak <nik@linuxlovers.at> in bug #137724. + +*ejabberd-1.1.1-r1 (12 Oct 2006) + + 12 Oct 2006; Tony Vroon <chainsaw@gentoo.org> + +files/ejabberd-1.1.1-r1.initd, +files/self-cert-v2.sh, +files/ssl.cnf, + ejabberd-1.1.1.ebuild, +ejabberd-1.1.1-r1.ebuild: + Revision bump, robust start/stop script thanks to Chris Carlin + <ccarlin@physics.tamu.edu> and Dustin J. Mitchell <dustin@v.igoro.us> in bug + #145373. Statsdx & SOCKS5 proxy support thanks to Nikolaus Polak + <nik@linuxlovers.at> in bug #137724. And finally, thanks to Micha Krause + <linux@krausam.de> for pointing out that the SSL eclass did not create + certificates usable for S2S connections in bug #150088. + + 01 Aug 2006; Joshua Jackson <tsunam@gentoo.org> ejabberd-1.1.1.ebuild: + Stable x86; bug #141302 + +*ejabberd-1.1.1 (19 Jun 2006) + + 19 Jun 2006; Tony Vroon <chainsaw@gentoo.org> +files/ejabberd-1.1.1.confd, + +files/ejabberd-1.1.1.initd, +ejabberd-1.1.1.ebuild: + Version bump, thanks to all contributors in bug #101708. + + 05 May 2006; Diego Pettenò <flameeyes@gentoo.org> ejabberd-0.7.5.ebuild: + Fix enewuser/enewgroup location, bug #130849. + + 23 Aug 2005; Gustavo Felisberto <humpback@gentoo.org>; + ejabberd-0.7.5.ebuild: + QA issue #103421 + + 16 Apr 2005; Gustavo Felisberto <humpback@gentoo.org>; files/ejabberd, + ejabberd-0.7.5.ebuild: + Small file permission patches + + 10 Apr 2005; Gustavo Felisberto <humpback@gentoo.org>; + files/ejabberd-0.7.5.initd, +files/self-cert.sh, ejabberd-0.7.5.ebuild: + Added ssl.pem generator script and einfo. + +*ejabberd-0.7.5 (08 Apr 2005) + + 08 Apr 2005; Gustavo Felisberto <humpback@gentoo.org>; +files/ejabberd, + +files/ejabberd-0.7.5.confd, +files/ejabberd-0.7.5.initd, + +files/ejabberdctl, +files/inetrc, +ejabberd-0.7.5.ebuild: + Initial import. This is masked for a reason :) if you have problems bug #63472 + is your friend. + diff --git a/net-im/ejabberd/Manifest b/net-im/ejabberd/Manifest new file mode 100644 index 0000000..9f5fba1 --- /dev/null +++ b/net-im/ejabberd/Manifest @@ -0,0 +1,18 @@ +AUX 2.1.0-mod_statsdx.patch 61403 RMD160 8a43feac4bee7e8c9e249a4c49248f8871c5b010 SHA1 2128c5f10555cdd28a182e1fd481c96af9fefcc5 SHA256 3c591e5c799b489c7b8566ca83d36edf5a28f782946b58e44edd4c2cfbd7f526 +AUX ejabberd-2.confd 840 RMD160 5227a3fbb0d0c8bffd8a5537003f965f1fb73582 SHA1 d3a51fa0923a571d30f3f0840834c651726ad206 SHA256 d6b0c44a450c4191e450b8e3ab281dc2e3bc668a97ddd1652d2e6c555675a2c6 +AUX ejabberd-2.initd 1134 RMD160 b5d3a5a50069be713511ebd37f9eab07dab33371 SHA1 0cd2c3bd44c1923014c1cdd84edfb56ddb11bdc2 SHA256 8b2c50bc80b5b0700195c79a4eaa6f68549fd63310b584c2e86d951c116e14de +AUX ejabberd-wrapper-2.template 1243 RMD160 989700850578dd86fe6cefeb465a1c84ba49df48 SHA1 115d10f04dd92ca090e853013dde3e5ffa3d6904 SHA256 1d3abfbb1b4dd79ba9fed74a5c86c97af70dc11927d8fa109a1486999d5f7a96 +AUX ejabberd-wrapper-3.template 1296 RMD160 c3c756e1f222a5f7043eebb7e566aee78a90a3aa SHA1 2e5ab01124c5f62ed90ca1c16d9151faedd80579 SHA256 264beec01828b57302a35c65ca52e63278fe5cb2109e129faffe44a53024f1bd +AUX ejabberd-wrapper.template 1251 RMD160 de7d9dcc0a2ee64ed9d52c0433d470635814c309 SHA1 faf30cdb5bac1285d4337447c37420a8b625789e SHA256 abf794ad03880ffd5893eb1caadc5bc9dc6de03fdb88d123711c8fb24435dde2 +AUX ejabberdctl 199 RMD160 1f4be5dcd018f0936baaeb41e2fd1c4a6a59bc62 SHA1 347200e8dd5790282cedb6a70c71fd4a6db9a0f5 SHA256 b88de8e8e5e8730ac7fe04b49ae3cf131c49a4e1ba451b35f1305d1c24a2dda0 +AUX ejabberdctl-wrapper-2.template 530 RMD160 f39037aac0f7ae65c2ca41bef59aa500553a7077 SHA1 84f340e60ce66b3b01c6e82122783fa590edf282 SHA256 6436820e8d015f7831464e0fb175074397ab9906ee8d552f97292acc3cd9e756 +AUX ejabberdctl-wrapper-3.template 908 RMD160 c5378d8e089ae1c180b7be76639a99d5cad16f11 SHA1 4ee6996c492360c4e44a05e011fb228eecff56b9 SHA256 c3c377ae8b00143e21ab4ccff7cffe539f6a6b95336aa5636cb8d6bba49c9592 +AUX inetrc 36 RMD160 4b79020864689ede547969610fde18fe490f5810 SHA1 1e0bae0f7251e2ae3b62ba9d3e5cc86bb5dd271e SHA256 0f383befc4c46134d88ce14d3bd06c404ef6575391f4ac0b5e8c28ba383b28fc +AUX self-cert-v2.sh 1017 RMD160 3beb0f05e8cc3041abd2f689d31d410bc7d5088d SHA1 1f07299b2e49541dcbf5c2b81b26280bbf0b6aeb SHA256 34b2c9cb36c424ffd1117bd20b67d0f4a05168b0bc6237e287c2dcabd0e27972 +AUX self-cert-v3.sh 2791 RMD160 23f07e5fdbaf4f946d74b1464396036d94f156ce SHA1 985fca31c76d3b5af39ba1209b317bdd3b6f4101 SHA256 bb3cf52bd4f67732f5b7c418ac61f7741c3cb009faaa109a68c0379338238072 +AUX self-cert.sh 491 RMD160 89bb577975eef172fa3c6e07b08d323162d1278b SHA1 61a4c8b79141ec1bc846e8ede6fa19a07210c619 SHA256 6a0c53a8573411c18ed6f5dd79ce4807b72fb10bc5eb3a3a7f4641c57e4ddceb +AUX ssl.cnf 1042 RMD160 47d2542942fb21f4be1e827d47eb4e0468e73910 SHA1 7347bae5a195ad158881fe5313f55ee41e85cb81 SHA256 ed066f7720fd9f4c2d57ffb2ebcbc4b2810d2b7ca22b67ec8c1dc1227baaa635 +DIST ejabberd-2.1.2.tar.gz 2232307 RMD160 0634422b10d43b0a4ce7826c911a0728bf56ff1c SHA1 e819b023c54a6878093813072b79590282d7d705 SHA256 354d6d1ecc1233b085d049963d5a90843f089b7d3d834809c410dbeb00974335 +EBUILD ejabberd-2.1.2.ebuild 5449 RMD160 5cdf9c2086a6fabfaaae4a7234279e62b4c67538 SHA1 6bda03d1be6d699d898dd6fcdfc00416f265efaf SHA256 e71793dab54daedada309eb692e9d9b562e847dd1f106b1f76a698f0213b1f20 +MISC ChangeLog 8965 RMD160 325a316bff3eb3d4c61170084e81dcebef9ad71c SHA1 f9b2b52117fc679eaf49884eae4cd059e40bf8f8 SHA256 016e4ed223c68bd48b80c59d0780c7b7e68753046da8dd83c59fb6eeec83683a +MISC metadata.xml 946 RMD160 b35c2362c1aaf5d99bf15270e61fc217317a79b7 SHA1 d85cb4971a4104d72456ef6a7ce7c5643937cf8d SHA256 c45048f833082afbc672e5bfd947de0a9793a6041ea76fb7afdfc9f0e02bd59d diff --git a/net-im/ejabberd/ejabberd-2.1.2.ebuild b/net-im/ejabberd/ejabberd-2.1.2.ebuild new file mode 100644 index 0000000..c7f8436 --- /dev/null +++ b/net-im/ejabberd/ejabberd-2.1.2.ebuild @@ -0,0 +1,163 @@ +# Copyright 1999-2010 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Header: $ + +EAPI=2 + +inherit eutils multilib pam + +DESCRIPTION="The Erlang Jabber Daemon" +HOMEPAGE="http://www.ejabberd.im/" +SRC_URI="http://www.process-one.net/downloads/${PN}/${PV}/${P}.tar.gz" + +LICENSE="GPL-2" +SLOT="0" +KEYWORDS="~amd64 ~arm ~ia64 ~ppc ~x86" +EJABBERD_MODULES="mod_irc mod_muc mod_proxy65 mod_pubsub" +IUSE="captcha debug ldap odbc pam ssl web zlib ${EJABBERD_MODULES}" + +DEPEND=">=net-im/jabber-base-0.01 + >=dev-libs/expat-1.95 + >=dev-lang/erlang-12.2.5[ssl?] + odbc? ( dev-db/unixODBC ) + ldap? ( =net-nds/openldap-2* ) + ssl? ( >=dev-libs/openssl-0.9.8e ) + captcha? ( media-gfx/imagemagick[truetype,png] ) + zlib? ( sys-libs/zlib )" +RDEPEND="${DEPEND}" + +PROVIDE="virtual/jabber-server" + +S=${WORKDIR}/${P}/src + +JABBER_ETC="/etc/jabber" +JABBER_RUN="/var/run/jabber" +JABBER_SPOOL="/var/spool/jabber" +JABBER_LOG="/var/log/jabber" +JABBER_DOC="/usr/share/doc/${PF}" + +src_prepare() { + if use mod_statsdx; then + ewarn "mod_statsdx is not a part of upstream tarball but is a third-party module" + ewarn "taken from here: http://www.ejabberd.im/mod_stats2file" + epatch "${FILESDIR}/2.1.0-mod_statsdx.patch" + fi + + sed -e "/^EJABBERDDIR[[:space:]]*=/{s:ejabberd:${PF}:}" \ + -e "/^ETCDIR[[:space:]]*=/{s:ejabberd:jabber:}" \ + -i Makefile.in || die + #sed -e "s:/share/doc/ejabberd/:${JABBER_DOC}:" -i web/ejabberd_web_admin.erl +} + +src_configure() { + econf \ + --docdir=/usr/share/doc/"${PF}"/html \ + --libdir=/usr/$(get_libdir)/erlang/lib/ \ + $(use_enable mod_irc) \ + $(use_enable ldap eldap) \ + $(use_enable mod_muc) \ + $(use_enable mod_proxy65) \ + $(use_enable mod_pubsub) \ + $(use_enable ssl tls) \ + $(use_enable web) \ + $(use_enable odbc) \ + $(use_enable zlib ejabberd_zlib) \ + $(use_enable pam) \ + --enable-user=jabber \ + || die "econf failed" +} + +src_compile() { + emake $(use debug && echo debug=true ejabberd_debug=true) || die "compiling ejabberd core failed" +} + +src_install() { + emake DESTDIR="${D}" install || die "install failed" + + if use ssl; then + insinto "/etc/ssl/ejabberd/" + newins "${FILESDIR}"/ssl.cnf ejabberd.cnf || die + + exeinto "${JABBER_DOC}/ssl" + cat "${FILESDIR}"/self-cert-v3.sh | \ + sed -e "s:@SSL_CERT@:/etc/ssl/ejabberd/ssl.pem:" \ + -e "s:@SSL_CONFIG@:/etc/ssl/ejabberd/ejabberd.cnf:" \ + > "${T}"/ssl-cert.sh || die "sed for self-cert.sh failed" + doexe "${T}/ssl-cert.sh" || die "installing self-cert.sh failed" + fi + + # Pam helper module permissions + # http://www.process-one.net/docs/ejabberd/guide_en.html + if use pam; then + pamd_mimic_system xmpp auth account || die "Cannot create pam.d file" + fperms 4750 "/usr/$(get_libdir)/erlang/lib/${P}/priv/bin/epam" || die "Cannot adjust epam permissions" + fi + + cd "${WORKDIR}/${P}/doc" + dodoc "release_notes_${PV%%_rc*}.txt" + rm "${D}/usr/share/doc/${PF}"/html/*.txt + chmod -x "${D}/usr/share/doc/${PF}"/html/* + + # set up /usr/sbin/ejabberd wrapper + cat "${FILESDIR}/ejabberd-wrapper-3.template" \ + | sed -e "s/@libdir@/$(get_libdir)/g;s/@version@/${PV}/g;s/@doc@/${PF}/g" \ + > "${T}/ejabberd" + exeinto /usr/sbin + doexe "${T}/ejabberd" || die + + # set up /usr/sbin/ejabberdctl wrapper + cat "${FILESDIR}/ejabberdctl-wrapper-3.template" \ + | sed -e "s/@libdir@/$(get_libdir)/g;s/@version@/${PV}/g;s/@doc@/${PF}/g" \ + > "${T}/ejabberdctl" + doexe "${T}/ejabberdctl" || die + + dodir /var/lib/ejabberd + newinitd "${FILESDIR}/${PN}-2.initd" ${PN} || die "Cannot install init.d script" + newconfd "${FILESDIR}/${PN}-2.confd" ${PN} || die "Cannot install conf.d file" + + # fix up the ssl cert paths in /etc/jabber/ejabberd.cfg to use the cert + # that would be generated by self-cert.sh + sed -i -e "s:/path/to/ssl.pem:/etc/ssl/ejabberd/ssl.pem:g" \ + "${D}${JABBER_ETC}/ejabberd.cfg" || die "Cannot sed ejabberd.cfg" + + # correct path to captcha script in default ejabberd.cfg + sed -r 's|\{captcha_cmd,[[:space:]]*".+"\}|{captcha_cmd, "/usr/'$(get_libdir)'/erlang/lib/'${P}'/priv/bin/captcha.sh"}|' -i \ + "${D}${JABBER_ETC}/ejabberd.cfg" || die "Cannot sed ejabberd.cfg" + + # if mod_irc is not enabled, comment out the mod_irc in the default + # ejabberd.cfg + if ! use mod_irc; then + sed -i -e "s/{mod_irc,/%{mod_irc,/" \ + "${D}${JABBER_ETC}/ejabberd.cfg" || die "Cannot sed ejabberd.cfg" + fi +} + +pkg_postinst() { + elog "For configuration instructions, please see" + elog "/usr/share/doc/${PF}/html/guide.html, or the online version at" + elog "http://www.process-one.net/en/projects/ejabberd/docs/guide_en.html" + + if use ssl ; then + if [ ! -e /etc/ssl/ejabberd/ssl.pem ]; then + elog "Please edit /etc/ssl/ssl.cnf" + elog "and run ${JABBER_DOC}/self-cert.sh." + elog "Ejabberd may refuse to start without an SSL certificate" + fi + fi + + if ! use web ; then + elog "The web USE flag is off, this has disabled the web admin interface." + fi + + elog '====================================================================' + elog 'Quick Start Guide:' + elog '1) Add output of `hostname -f` to /etc/jabber/ejabberd.cfg line 89' + elog ' {hosts, ["localhost", "thehost"]}.' + elog '2) Add an admin user to /etc/jabber/ejabberd.cfg line 324' + elog ' {acl, admin, {user, "theadmin", "thehost"}}.' + elog '3) Start the server' + elog ' # /etc/init.d/ejabberd start' + elog '4) Register the admin user' + elog ' # /usr/sbin/ejabberdctl register theadmin thehost thepassword' + elog '5) Log in with your favourite jabber client or using the web admin' +} diff --git a/net-im/ejabberd/files/2.1.0-mod_statsdx.patch b/net-im/ejabberd/files/2.1.0-mod_statsdx.patch new file mode 100644 index 0000000..a8e5881 --- /dev/null +++ b/net-im/ejabberd/files/2.1.0-mod_statsdx.patch @@ -0,0 +1,1895 @@ +diff -Naur ./ejabberd-2.1.0/src/mod_stats2file.erl ./ejabberd-2.1.0-new/src/mod_stats2file.erl +--- mod_stats2file.erl 1970-01-01 03:00:00.000000000 +0300 ++++ mod_stats2file.erl 2007-12-08 20:00:59.000000000 +0300 +@@ -0,0 +1,409 @@ ++%%%---------------------------------------------------------------------- ++%%% File : mod_stats2file.erl ++%%% Author : Badlop <badlop@ono.com> ++%%% Purpose : Generates files with all kind of statistics ++%%% Created : ++%%% Id : $Id: mod_stats2file.erl 440 2007-12-06 22:36:21Z badlop $ ++%%%---------------------------------------------------------------------- ++ ++-module(mod_stats2file). ++-author('badlop@ono.com'). ++ ++-behaviour(gen_mod). ++ ++-export([start/2, loop/5, stop/1]). ++ ++-include("ejabberd.hrl"). ++-include("jlib.hrl"). ++-include("mod_roster.hrl"). ++ ++-define(PROCNAME, ejabberd_mod_stats2file). ++-define(T(Text), translate:translate("Lang", Text)). ++ ++%% ------------------- ++%% Module control ++%% ------------------- ++ ++start(_Host, Opts) -> ++ case whereis(?PROCNAME) of ++ undefined -> ++ Interval = gen_mod:get_opt(interval, Opts, 5), ++ I = Interval*60*1000, ++ %I = 9000, %+++ ++ ++ Type = gen_mod:get_opt(type, Opts, html), ++ ++ Split = gen_mod:get_opt(split, Opts, false), ++ ++ BaseFilename = gen_mod:get_opt(basefilename, Opts, "/tmp/ejasta"), ++ ++ Hosts_all = ejabberd_config:get_global_option(hosts), ++ Hosts = gen_mod:get_opt(hosts, Opts, Hosts_all), ++ ++ register(?PROCNAME, spawn(?MODULE, loop, [I, Hosts, BaseFilename, Type, Split])); ++ _ -> ++ ok ++ end, ++ ok. ++ ++loop(I, Hs, O, T, Split) -> ++ write_statsfiles(Split, I, Hs, O, T), ++ timer:send_after(I, stats), ++ receive ++ stats -> ?MODULE:loop(I, Hs, O, T, Split); ++ stop -> ok ++ end. ++ ++stop(_Host) -> ++ case whereis(?PROCNAME) of ++ undefined -> ok; ++ _ -> ++ ?PROCNAME ! stop ++ end. ++ ++ ++%% ------------------- ++%% write_stat* ++%% ------------------- ++ ++write_statsfiles(false, I, Hs, O, T) -> ++ Fn = filename:flatten([O, ".", T]), ++ {ok, F} = file:open(Fn, [write]), ++ fwini(F, T), ++ write_stats(I, server, "", F, T), ++ fwbr(F, T), ++ fwbr(F, T), ++ Node = node(), ++ write_stats(I, node, Node, F, T), ++ lists:foreach( ++ fun(H) -> ++ fwbr(F, T), ++ fwbr(F, T), ++ write_stats(I, vhost, H, F, T) ++ end, ++ Hs), ++ fwend(F, T), ++ file:close(F); ++ ++write_statsfiles(true, I, Hs, O, T) -> ++ write_statsfile(I, server, "", O, T), ++ Node = node(), ++ write_statsfile(I, node, Node, O, T), ++ lists:foreach( ++ fun(H) -> ++ write_statsfile(I, vhost, H, O, T) ++ end, ++ Hs). ++ ++write_statsfile(I, Class, Name, O, T) -> ++ Fn = filename:flatten([O, "-", Class, "-", Name, ".", T]), ++ {ok, F} = file:open(Fn, [write]), ++ fwini(F, T), ++ write_stats(I, Class, Name, F, T), ++ fwend(F, T), ++ file:close(F). ++ ++write_stats(I, server, _Name, F, T) -> ++ fwh(F, "Server statistics", 1, T), ++ fwbl1(F, T), ++ ++ fwtstl(F, "localtime", T), ++ ++ fwh(F, "Accounts", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "registeredusers", T), ++ fwbl2(F, T), ++ ++ fwh(F, "Roster", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "totalrosteritems", T), ++ fwttl(F, "meanitemsinroster", T), ++ fwbl2(F, T), ++ ++ fwh(F, "Users", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "onlineusers", T), ++ fwttl(F, "offlinemsg", T), ++ fwttl(F, "vcards", T), ++ fwbl2(F, T), ++ ++ fwh(F, "MUC", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "totalmucrooms", T), ++ fwttl(F, "permmucrooms", T), ++ fwttl(F, "regmucrooms", T), ++ fwbl2(F, T), ++ ++ fwh(F, "Pub/Sub", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "regpubsubnodes", T), ++ fwbl2(F, T), ++ ++ %fwh(F, "IRC", 2, T), ++ %fwbl1(F, T), ++ %fwttl(F, "ircconns", T), ++ %fwbl2(F, T), ++ ++ fwh(F, "Ratios", 2, T), ++ fwbl1(F, T), ++ fwttl(F, {"user_login", I}, server, T), ++ fwttl(F, {"user_logout", I}, server, T), ++ fwttl(F, {"remove_user", I}, server, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Sessions", 2, T), ++ fwbl1(F, T), ++ fwh(F, "Clients", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "client", server, T), ++ ++ fwbl2(F, T), ++ fwh(F, "OS", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "os", server, T), ++ fwbl2(F, T), ++ ++ case T of ++ html -> ++ fwh(F, "Client/OS", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "client_os", server, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Languages", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "languages", server, T), ++ fwbl2(F, T), ++ fwbl2(F, T); ++ _ -> ++ ok ++ end, ++ ++ fwbl2(F, T); ++ ++write_stats(I, node, Node, F, T) -> ++ fwh(F, "Node statistics", 1, T), ++ fwbl1(F, T), ++ ++ fwt(F, "Node", Node, T), ++ ++ fwh(F, "Connections", 2, T), ++ fwbl1(F, T), ++ %fwttl(F, "plainusers", T), ++ %fwttl(F, "sslusers", T), ++ %fwttl(F, "tlsusers", T), ++ fwttl(F, "httppollusers", T), ++ fwttl(F, "httpbindusers", T), ++ fwttl(F, "s2sconnections", T), ++ fwttl(F, "s2sservers", T), ++ fwbl2(F, T), ++ ++ fwh(F, "Erlang", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "operatingsystem", T), ++ fwttl(F, "erlangmachine", T), ++ fwttl(F, "erlangmachinetarget", T), ++ fwttl(F, "maxprocallowed", T), ++ fwttl(F, "totalerlproc", T), ++ fwttl(F, "procqueue", T), ++ fwbl2(F, T), ++ ++ fwh(F, "Times", 2, T), ++ fwbl1(F, T), ++ %fwttl(F, "uptimehuman", T), ++ %fwttl(F, "lastrestart", T), ++ ++ fwbr(F, T), ++ CPUTime = element(1, rpc:call(Node, erlang, statistics, [runtime])), ++ fw(F, "~s (ms): ~w",[?T("CPUtime"), CPUTime]), ++ ++ fwbr(F, T), ++ MT = trunc(erlang:memory(total)/1024), ++ fwt(F, "Memory VM (KB)", MT, T), ++ ++ fwbl2(F, T), ++ ++ fwh(F, "CPU", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "cpu_avg1", T), ++ fwttl(F, "cpu_avg5", T), ++ fwttl(F, "cpu_avg15", T), ++ fwttl(F, "cpu_nprocs", T), ++ U = cpu_sup:util([detailed]), ++ fwttl(F, {"cpu_util_user", U}, T), ++ fwttl(F, {"cpu_util_nice_user", U}, T), ++ fwttl(F, {"cpu_util_kernel", U}, T), ++ fwttl(F, {"cpu_util_idle", U}, T), ++ fwttl(F, {"cpu_util_wait", U}, T), ++ fwbl2(F, T), ++ ++ fwh(F, "RAM", 2, T), ++ fwbl1(F, T), ++ M = memsup:get_system_memory_data(), ++ fwttl(F, {"memsup_system", M}, T), ++ fwttl(F, {"memsup_free", M}, T), ++ fwttl(F, {"reductions", I}, T), ++ fwbl2(F, T), ++ ++ fwbl2(F, T); ++ ++write_stats(I, vhost, Host, F, T) -> ++ fwh(F, "Host statistics", 1, T), ++ fwbl1(F, T), ++ ++ fwtstl(F, "vhost", Host, T), ++ ++ fwh(F, "Accounts", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "registeredusers", Host, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Roster", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "totalrosteritems", Host, T), ++ fwttl(F, "meanitemsinroster", Host, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Users", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "onlineusers", Host, T), ++ fwttl(F, "offlinemsg", Host, T), ++ fwttl(F, "vcards", Host, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Connections", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "s2sconnections", Host, T), ++ fwbl2(F, T), ++ ++ fwh(F, "MUC", 2, T), ++ fwbl1(F, T), ++ fwttl(F, "totalmucrooms", Host, T), ++ fwttl(F, "permmucrooms", Host, T), ++ fwttl(F, "regmucrooms", Host, T), ++ fwbl2(F, T), ++ ++ %fwh(F, "IRC", 2, T), ++ %fwbl1(F, T), ++ %fwttl(F, "ircconns", Host, T), ++ %fwbl2(F, T), ++ ++ fwh(F, "Sessions", 2, T), ++ fwbl1(F, T), ++ fwh(F, "Clients", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "client", Host, T), ++ ++ fwbl2(F, T), ++ fwh(F, "OS", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "os", Host, T), ++ fwbl2(F, T), ++ ++ case T of ++ html -> ++ fwh(F, "Client/OS", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "client_os", Host, T), ++ fwbl2(F, T), ++ ++ fwh(F, "Languages", 3, T), ++ fwbl1(F, T), ++ do_stat_table(F, "languages", Host, T), ++ fwbl2(F, T), ++ fwbl2(F, T); ++ _ -> ++ ok ++ end, ++ ++ fwh(F, "Ratios", 2, T), ++ fwbl1(F, T), ++ fwttl(F, {"user_login", I}, Host, T), ++ fwttl(F, {"user_logout", I}, Host, T), ++ fwttl(F, {"remove_user", I}, Host, T), ++ fwttl(F, {send, iq, in, I}, Host, T), ++ fwttl(F, {send, iq, out, I}, Host, T), ++ fwttl(F, {send, message, in, I}, Host, T), ++ fwttl(F, {send, message, out, I}, Host, T), ++ fwttl(F, {send, presence, in, I}, Host, T), ++ fwttl(F, {send, presence, out, I}, Host, T), ++ fwttl(F, {recv, iq, in, I}, Host, T), ++ fwttl(F, {recv, iq, out, I}, Host, T), ++ fwttl(F, {recv, message, in, I}, Host, T), ++ fwttl(F, {recv, message, out, I}, Host, T), ++ fwttl(F, {recv, presence, in, I}, Host, T), ++ fwttl(F, {recv, presence, out, I}, Host, T), ++ fwbl2(F, T), ++ ++ fwbl2(F, T). ++ ++%% ------------------- ++%% get(* ++%% ------------------- ++ ++fwttl(F, Arg, T) -> fwt(F, gett(Arg), getl(Arg), T). ++fwttl(F, Arg, Host, T) -> fwt(F, gett(Arg), getl(Arg, Host), T). ++ ++fwtstl(F, Arg, T) -> fwts(F, gett(Arg), getl(Arg), T). ++fwtstl(F, Arg, Host, T) -> fwts(F, gett(Arg), getl(Arg, Host), T). ++ ++gett(Arg) -> get(node(), [Arg, title]). ++getl(Args) -> get(node(), [Args]). ++getl(Args, Host) -> get(node(), [Args, Host]). ++ ++get(Node, A) -> ++ mod_statsdx:get_statistic(Node, A). ++ ++ ++%% ------------------- ++%% utilities ++%% ------------------- ++ ++fw(F, S) -> file:write(F, S). ++fw(F, S, O) -> file:write(F, io_lib:format(S, O)). ++ ++fwt(F, S, O, html) -> fw(F, "~s: ~p<br/>~n",[?T(S), O]); ++fwt(F, S, O, txt) -> fw(F, "~s: ~p~n",[?T(S), O]); ++fwt(F, _, O, dat) -> fw(F, "~p~n",[O]). ++ ++fwts(F, S, O, html) -> fw(F, "~s: ~s<br/>~n",[?T(S), O]); ++fwts(F, S, O, txt) -> fw(F, "~s: ~s~n",[?T(S), O]); ++fwts(F, _, O, dat) -> fw(F, "~s~n",[O]). ++ ++%fwtsn(F, S, O, html) -> fw(F, "~s: ~s<br/>",[?T(S), O]); ++%fwtsn(F, S, O, txt) -> fw(F, "~s: ~s",[?T(S), O]); ++%fwtsn(F, _, O, dat) -> fw(F, "~s",[O]). ++ ++fwh(F, S, N, html) -> fw(F, "<h~p>~s</h~p>~n",[N, S, N]); ++fwh(F, S, 1, txt) -> fw(F, " ===== ~s =====~n",[S]); ++fwh(F, S, 2, txt) -> fw(F, "~n --- ~s ---~n",[S]); ++fwh(F, S, 3, txt) -> fw(F, "~n + ~s +~n",[S]); ++fwh(_, _, _, dat) -> ok. ++ ++fwbr(F, html) -> fw(F, "<br/>\n"); ++fwbr(F, txt) -> fw(F, "\n"); ++fwbr(_, dat) -> ok. ++ ++fwini(F, html) -> fw(F, "<body>\n"); ++fwini(_, txt) -> ok; ++fwini(_, dat) -> ok. ++fwend(F, html) -> fw(F, "</body>\n"); ++fwend(_, txt) -> ok; ++fwend(_, dat) -> ok. ++ ++fwbl1(F, html) -> fw(F, "<blockquote>\n"); ++fwbl1(_, txt) -> ok; ++fwbl1(_, dat) -> ok. ++fwbl2(F, html) -> fw(F, "</blockquote>\n"); ++fwbl2(_, txt) -> ok; ++fwbl2(_, dat) -> ok. ++ ++do_stat_table(F, Stat, Host, T) -> ++ do_stat_table(F, Stat, Host, T, unknown). ++do_stat_table(F, Stat, Host, T, _Lang) -> ++ lists:map( ++ fun({Name, Value}) -> ++ fwts(F, Name, io_lib:format("~p", [Value]), T) ++ end, ++ mod_statsdx:get_statistic(global, [Stat, Host]) ++ ). +diff -Naur ./ejabberd-2.1.0/src/mod_statsdx.erl ./ejabberd-2.1.0-new/src/mod_statsdx.erl +--- mod_statsdx.erl 1970-01-01 03:00:00.000000000 +0300 ++++ mod_statsdx.erl 2009-12-03 00:29:43.000000000 +0300 +@@ -0,0 +1,1478 @@ ++%%%---------------------------------------------------------------------- ++%%% File : mod_statsdx.erl ++%%% Author : Badlop <badlop@ono.com> ++%%% Purpose : Calculates and gathers statistics actively ++%%% Created : ++%%% Id : $Id: mod_statsdx.erl 1038 2009-11-24 12:34:03Z badlop $ ++%%%---------------------------------------------------------------------- ++ ++%%%% Definitions ++ ++-module(mod_statsdx). ++-author('badlop@ono.com'). ++ ++-behaviour(gen_mod). ++ ++-export([start/2, loop/1, stop/1, get_statistic/2, ++ %% Commands ++ getstatsdx/1, getstatsdx/2, ++ %% WebAdmin ++ web_menu_main/2, web_page_main/2, ++ web_menu_node/3, web_page_node/5, ++ web_menu_host/3, web_page_host/3, ++ %% Hooks ++ remove_user/2, user_send_packet/3, ++ user_send_packet_traffic/3, user_receive_packet_traffic/4, ++ user_login/1, user_logout/4, user_logout_sm/3]). ++ ++-include("ejabberd.hrl"). ++-include("ejabberd_commands.hrl"). ++-include("jlib.hrl"). ++-include("mod_roster.hrl"). ++-include("web/ejabberd_http.hrl"). ++-include("web/ejabberd_web_admin.hrl"). ++ ++-define(PROCNAME, ejabberd_mod_statsdx). ++ ++%% Copied from ejabberd_s2s.erl Used in function get_s2sconnections/1 ++-record(s2s, {fromto, pid, key}). ++ ++%%%================================== ++%%%% Module control ++ ++start(Host, Opts) -> ++ Hooks = gen_mod:get_opt(hooks, Opts, false), ++ %% Default value for the counters ++ CD = case Hooks of ++ true -> 0; ++ traffic -> 0; ++ false -> "disabled" ++ end, ++ ++ ejabberd_commands:register_commands(commands()), ++ ++ %% If the process that handles statistics for the server is not started yet, ++ %% start it now ++ case whereis(?PROCNAME) of ++ undefined -> ++ application:start(os_mon), ++ initialize_stats_server(); ++ _ -> ++ ok ++ end, ++ ?PROCNAME ! {initialize_stats, Host, Hooks, CD}. ++ ++stop(Host) -> ++ finish_stats(Host), ++ ejabberd_commands:unregister_commands(commands()), ++ case whereis(?PROCNAME) of ++ undefined -> ok; ++ _ -> ?PROCNAME ! {stop, Host} ++ end. ++ ++ ++%%%================================== ++%%%% Stats Server ++ ++table_name(server) -> gen_mod:get_module_proc("server", mod_statsdx); ++table_name(Host) -> gen_mod:get_module_proc(Host, mod_statsdx). ++ ++initialize_stats_server() -> ++ register(?PROCNAME, spawn(?MODULE, loop, [[]])). ++ ++loop(Hosts) -> ++ receive ++ {initialize_stats, Host, Hooks, CD} -> ++ case Hosts of ++ [] -> prepare_stats_server(CD); ++ _ -> ok ++ end, ++ prepare_stats_host(Host, Hooks, CD), ++ loop([Host | Hosts]); ++ {stop, Host} -> ++ case Hosts -- [Host] of ++ [] -> ++ finish_stats(); ++ RemainingHosts -> ++ loop(RemainingHosts) ++ end ++ end. ++ ++%% Si no existe una tabla de stats del server, crearla. ++%% Deberia ser creada por un proceso que solo muera cuando se detenga el ultimo mod_statsdx del servidor ++prepare_stats_server(CD) -> ++ Table = table_name("server"), ++ ets:new(Table, [named_table, public]), ++ ets:insert(Table, {{user_login, server}, CD}), ++ ets:insert(Table, {{user_logout, server}, CD}), ++ ets:insert(Table, {{remove_user, server}, CD}), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{client, server, E}, CD}) end, ++ list_elem(clients, id) ++ ), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{conntype, server, E}, CD}) end, ++ list_elem(conntypes, id) ++ ), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{os, server, E}, CD}) end, ++ list_elem(oss, id) ++ ), ++ ejabberd_hooks:add(webadmin_menu_main, ?MODULE, web_menu_main, 50), ++ ejabberd_hooks:add(webadmin_menu_node, ?MODULE, web_menu_node, 50), ++ ejabberd_hooks:add(webadmin_page_main, ?MODULE, web_page_main, 50), ++ ejabberd_hooks:add(webadmin_page_node, ?MODULE, web_page_node, 50). ++ ++prepare_stats_host(Host, Hooks, CD) -> ++ Table = table_name(Host), ++ ets:new(Table, [named_table, public]), ++ ets:insert(Table, {{user_login, Host}, CD}), ++ ets:insert(Table, {{user_logout, Host}, CD}), ++ ets:insert(Table, {{remove_user, Host}, CD}), ++ ets:insert(Table, {{send, Host, iq, in}, CD}), ++ ets:insert(Table, {{send, Host, iq, out}, CD}), ++ ets:insert(Table, {{send, Host, message, in}, CD}), ++ ets:insert(Table, {{send, Host, message, out}, CD}), ++ ets:insert(Table, {{send, Host, presence, in}, CD}), ++ ets:insert(Table, {{send, Host, presence, out}, CD}), ++ ets:insert(Table, {{recv, Host, iq, in}, CD}), ++ ets:insert(Table, {{recv, Host, iq, out}, CD}), ++ ets:insert(Table, {{recv, Host, message, in}, CD}), ++ ets:insert(Table, {{recv, Host, message, out}, CD}), ++ ets:insert(Table, {{recv, Host, presence, in}, CD}), ++ ets:insert(Table, {{recv, Host, presence, out}, CD}), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{client, Host, E}, CD}) end, ++ list_elem(clients, id) ++ ), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{conntype, Host, E}, CD}) end, ++ list_elem(conntypes, id) ++ ), ++ lists:foreach( ++ fun(E) -> ets:insert(Table, {{os, Host, E}, CD}) end, ++ list_elem(oss, id) ++ ), ++ case Hooks of ++ true -> ++ ejabberd_hooks:add(remove_user, Host, ?MODULE, remove_user, 90), ++ ejabberd_hooks:add(user_available_hook, Host, ?MODULE, user_login, 90), ++ %%ejabberd_hooks:add(unset_presence_hook, Host, ?MODULE, user_logout, 90), ++ ejabberd_hooks:add(sm_remove_connection_hook, Host, ?MODULE, user_logout_sm, 90), ++ ejabberd_hooks:add(user_send_packet, Host, ?MODULE, user_send_packet, 90); ++ traffic -> ++ ejabberd_hooks:add(user_receive_packet, Host, ?MODULE, user_receive_packet_traffic, 92), ++ ejabberd_hooks:add(user_send_packet, Host, ?MODULE, user_send_packet_traffic, 92), ++ ejabberd_hooks:add(remove_user, Host, ?MODULE, remove_user, 90), ++ ejabberd_hooks:add(user_available_hook, Host, ?MODULE, user_login, 90), ++ ejabberd_hooks:add(sm_remove_connection_hook, Host, ?MODULE, user_logout_sm, 90), ++ ejabberd_hooks:add(user_send_packet, Host, ?MODULE, user_send_packet, 90); ++ false -> ++ ok ++ end, ++ ejabberd_hooks:add(webadmin_menu_host, Host, ?MODULE, web_menu_host, 50), ++ ejabberd_hooks:add(webadmin_page_host, Host, ?MODULE, web_page_host, 50). ++ ++finish_stats() -> ++ ejabberd_hooks:delete(webadmin_menu_main, ?MODULE, web_menu_main, 50), ++ ejabberd_hooks:delete(webadmin_menu_node, ?MODULE, web_menu_node, 50), ++ ejabberd_hooks:delete(webadmin_page_main, ?MODULE, web_page_main, 50), ++ ejabberd_hooks:delete(webadmin_page_node, ?MODULE, web_page_node, 50), ++ Table = table_name("server"), ++ catch ets:delete(Table). ++ ++finish_stats(Host) -> ++ ejabberd_hooks:delete(user_available_hook, Host, ?MODULE, user_login, 90), ++ %%ejabberd_hooks:delete(unset_presence_hook, Host, ?MODULE, user_logout, 90), ++ ejabberd_hooks:delete(sm_remove_connection_hook, Host, ?MODULE, user_logout_sm, 90), ++ ejabberd_hooks:delete(user_send_packet, Host, ?MODULE, user_send_packet, 90), ++ ejabberd_hooks:delete(user_send_packet, Host, ?MODULE, user_send_packet_traffic, 92), ++ ejabberd_hooks:delete(user_receive_packet, Host, ?MODULE, user_receive_packet_traffic, 92), ++ ejabberd_hooks:delete(remove_user, Host, ?MODULE, remove_user, 90), ++ ejabberd_hooks:delete(webadmin_menu_host, Host, ?MODULE, web_menu_host, 50), ++ ejabberd_hooks:delete(webadmin_page_host, Host, ?MODULE, web_page_host, 50), ++ Table = table_name(Host), ++ catch ets:delete(Table). ++ ++ ++%%%================================== ++%%%% Hooks Handlers ++ ++remove_user(_User, Server) -> ++ Table = table_name(Server), ++ ets:update_counter(Table, {remove_user, Server}, 1), ++ ets:update_counter(Table, {remove_user, server}, 1). ++ ++user_send_packet(FromJID, ToJID, NewEl) -> ++ %% Registrarse para tramitar Host/mod_stats2file ++ case list_to_atom(ToJID#jid.lresource) of ++ ?MODULE -> received_response(FromJID, ToJID, NewEl); ++ _ -> ok ++ end. ++ ++user_send_packet_traffic(FromJID, ToJID, NewEl) -> ++ %% Only required for traffic stats ++ Host = FromJID#jid.lserver, ++ HostTo = ToJID#jid.lserver, ++ {xmlelement, Type, _, _} = NewEl, ++ Type2 = case Type of ++ "iq" -> iq; ++ "message" -> message; ++ "presence" -> presence ++ end, ++ Dest = case is_host(HostTo, Host) of ++ true -> in; ++ false -> out ++ end, ++ Table = table_name(Host), ++ ets:update_counter(Table, {send, Host, Type2, Dest}, 1). ++ ++%% Only required for traffic stats ++user_receive_packet_traffic(_JID, From, To, FixedPacket) -> ++ HostFrom = From#jid.lserver, ++ Host = To#jid.lserver, ++ {xmlelement, Type, _, _} = FixedPacket, ++ Type2 = case Type of ++ "iq" -> iq; ++ "message" -> message; ++ "presence" -> presence ++ end, ++ Dest = case is_host(HostFrom, Host) of ++ true -> in; ++ false -> out ++ end, ++ Table = table_name(Host), ++ ets:update_counter(Table, {recv, Host, Type2, Dest}, 1). ++ ++ ++%%%================================== ++%%%% get(* ++ ++%%gett(Arg) -> get(node(), [Arg, title]). ++getl(Args) -> get(node(), [Args]). ++getl(Args, Host) -> get(node(), [Args, Host]). ++ ++%%get(_Node, ["", title]) -> ""; ++ ++get_statistic(N, A) -> ++ case catch get(N, A) of ++ {'EXIT', R} -> ++ ?ERROR_MSG("get_statistic error for N: ~p, A: ~p~n~p", [N, A, R]), ++ unknown; ++ Res -> Res ++ end. ++ ++get(global, A) -> get(node(), A); ++ ++get(_, [{"reductions", _}, title]) -> "Reductions (per minute)"; ++get(_, [{"reductions", I}]) -> calc_avg(element(2, statistics(reductions)), I); %+++ ++ ++get(_, ["cpu_avg1", title]) -> "Average system load (1 min)"; ++get(N, ["cpu_avg1"]) -> rpc:call(N, cpu_sup, avg1, [])/256; ++get(_, ["cpu_avg5", title]) -> "Average system load (5 min)"; ++get(N, ["cpu_avg5"]) -> rpc:call(N, cpu_sup, avg1, [])/256; ++get(_, ["cpu_avg15", title]) -> "Average system load (15 min)"; ++get(N, ["cpu_avg15"]) -> rpc:call(N, cpu_sup, avg15, [])/256; ++get(_, ["cpu_nprocs", title]) -> "Number of UNIX processes running on this machine"; ++get(N, ["cpu_nprocs"]) -> rpc:call(N, cpu_sup, nprocs, []); ++get(_, ["cpu_util", title]) -> "CPU utilization"; ++get(N, ["cpu_util"]) -> rpc:call(N, cpu_sup, util, []); ++ ++get(_, [{"cpu_util_user", _}, title]) -> "CPU utilization - user"; ++get(_, [{"cpu_util_nice_user", _}, title]) -> "CPU utilization - nice_user"; ++get(_, [{"cpu_util_kernel", _}, title]) -> "CPU utilization - kernel"; ++get(_, [{"cpu_util_wait", _}, title]) -> "CPU utilization - wait"; ++get(_, [{"cpu_util_idle", _}, title]) -> "CPU utilization - idle"; ++get(_, [{"cpu_util_user", U}]) -> proplists:get_value(user, element(2, U), -1); ++get(_, [{"cpu_util_nice_user", U}]) -> proplists:get_value(nice_user, element(2, U), -1); ++get(_, [{"cpu_util_kernel", U}]) -> proplists:get_value(kernel, element(2, U), -1); ++get(_, [{"cpu_util_wait", U}]) -> proplists:get_value(wait, element(3, U), -1); ++get(_, [{"cpu_util_idle", U}]) -> proplists:get_value(idle, element(3, U), -1); ++ ++get(_, [{"client", Id}, title]) -> atom_to_list(Id); ++get(_, [{"client", Id}, Host]) -> ++ Table = table_name(Host), ++ case ets:lookup(Table, {client, Host, Id}) of ++ [{_, C}] -> C; ++ [] -> 0 ++ end; ++get(_, ["client", title]) -> "Client"; ++get(N, ["client", Host]) -> ++ lists:map( ++ fun(Id) -> ++ [Id_string] = io_lib:format("~p", [Id]), ++ {Id_string, get(N, [{"client", Id}, Host])} ++ end, ++ lists:usort(list_elem(clients, id)) ++ ); ++ ++get(_, [{"os", Id}, title]) -> atom_to_list(Id); ++get(_, [{"os", _Id}, list]) -> lists:usort(list_elem(oss, id)); ++get(_, [{"os", Id}, Host]) -> [{_, C}] = ets:lookup(table_name(Host), {os, Host, Id}), C; ++get(_, ["os", title]) -> "Operating System"; ++get(N, ["os", Host]) -> ++ lists:map( ++ fun(Id) -> ++ [Id_string] = io_lib:format("~p", [Id]), ++ {Id_string, get(N, [{"os", Id}, Host])} ++ end, ++ lists:usort(list_elem(oss, id)) ++ ); ++ ++get(_, [{"conntype", Id}, title]) -> atom_to_list(Id); ++get(_, [{"conntype", _Id}, list]) -> lists:usort(list_elem(conntypes, id)); ++get(_, [{"conntype", Id}, Host]) -> [{_, C}] = ets:lookup(table_name(Host), {conntype, Host, Id}), C; ++get(_, ["conntype", title]) -> "Connection Type"; ++get(N, ["conntype", Host]) -> ++ lists:map( ++ fun(Id) -> ++ [Id_string] = io_lib:format("~p", [Id]), ++ {Id_string, get(N, [{"conntype", Id}, Host])} ++ end, ++ lists:usort(list_elem(conntypes, id)) ++ ); ++ ++get(_, [{"memsup_system", _}, title]) -> "Memory physical (bytes)"; ++get(_, [{"memsup_system", M}]) -> proplists:get_value(system_total_memory, M, -1); ++get(_, [{"memsup_free", _}, title]) -> "Memory free (bytes)"; ++get(_, [{"memsup_free", M}]) -> proplists:get_value(free_memory, M, -1); ++ ++get(_, [{"user_login", _}, title]) -> "Logins (per minute)"; ++get(_, [{"user_login", I}, Host]) -> get_stat({user_login, Host}, I); ++get(_, [{"user_logout", _}, title]) -> "Logouts (per minute)"; ++get(_, [{"user_logout", I}, Host]) -> get_stat({user_logout, Host}, I); ++get(_, [{"remove_user", _}, title]) -> "Accounts deleted (per minute)"; ++get(_, [{"remove_user", I}, Host]) -> get_stat({remove_user, Host}, I); ++get(_, [{Table, Type, Dest, _}, title]) -> filename:flatten([Table, Type, Dest]); ++get(_, [{Table, Type, Dest, I}, Host]) -> get_stat({Table, Host, Type, Dest}, I); ++ ++get(_, ["user_login", title]) -> "Logins"; ++get(_, ["user_login", Host]) -> get_stat({user_login, Host}); ++get(_, ["user_logout", title]) -> "Logouts"; ++get(_, ["user_logout", Host]) -> get_stat({user_logout, Host}); ++get(_, ["remove_user", title]) -> "Accounts deleted"; ++get(_, ["remove_user", Host]) -> get_stat({remove_user, Host}); ++get(_, [{Table, Type, Dest}, title]) -> filename:flatten([Table, Type, Dest]); ++get(_, [{Table, Type, Dest}, Host]) -> get_stat({Table, Host, Type, Dest}); ++ ++get(_, ["localtime", title]) -> "Local time"; ++get(N, ["localtime"]) -> ++ localtime_to_string(rpc:call(N, erlang, localtime, [])); ++ ++get(_, ["memory_total", title]) -> "Memory total allocated: processes and system"; ++get(N, ["memory_total"]) -> rpc:call(N, erlang, memory, [total]); ++get(_, ["memory_processes", title]) -> "Memory allocated by Erlang processes"; ++get(N, ["memory_processes"]) -> rpc:call(N, erlang, memory, [processes]); ++get(_, ["memory_processes_used", title]) -> "Memory used by Erlang processes"; ++get(N, ["memory_processes_used"]) -> rpc:call(N, erlang, memory, [processes_used]); ++get(_, ["memory_system", title]) -> "Memory allocated by Erlang emulator but not associated to processes"; ++get(N, ["memory_system"]) -> rpc:call(N, erlang, memory, [system]); ++get(_, ["memory_atom", title]) -> "Memory allocated for atoms"; ++get(N, ["memory_atom"]) -> rpc:call(N, erlang, memory, [atom]); ++get(_, ["memory_atom_used", title]) -> "Memory used for atoms"; ++get(N, ["memory_atom_used"]) -> rpc:call(N, erlang, memory, [atom_used]); ++get(_, ["memory_binary", title]) -> "Memory allocated for binaries"; ++get(N, ["memory_binary"]) -> rpc:call(N, erlang, memory, [binary]); ++get(_, ["memory_code", title]) -> "Memory allocated for Erlang code"; ++get(N, ["memory_code"]) -> rpc:call(N, erlang, memory, [code]); ++get(_, ["memory_ets", title]) -> "Memory allocated for ETS tables"; ++get(N, ["memory_ets"]) -> rpc:call(N, erlang, memory, [ets]); ++ ++get(_, ["vhost", title]) -> "Virtual host"; ++get(_, ["vhost", Host]) -> Host; ++ ++get(_, ["ejabberdversion", title]) -> "ejabberd version"; ++get(N, ["ejabberdversion"]) -> element(2, rpc:call(N, application, get_key, [ejabberd, vsn])); ++ ++get(_, ["totalerlproc", title]) -> "Total Erlang processes running"; ++get(N, ["totalerlproc"]) -> rpc:call(N, erlang, system_info, [process_count]); ++get(_, ["operatingsystem", title]) -> "Operating System"; ++get(N, ["operatingsystem"]) -> {rpc:call(N, os, type, []), rpc:call(N, os, version, [])}; ++get(_, ["erlangmachine", title]) -> "Erlang machine"; ++get(N, ["erlangmachine"]) -> rpc:call(N, erlang, system_info, [system_version]); ++get(_, ["erlangmachinetarget", title]) -> "Erlang machine target"; ++get(N, ["erlangmachinetarget"]) -> rpc:call(N, erlang, system_info, [system_architecture]); ++get(_, ["maxprocallowed", title]) -> "Maximum processes allowed"; ++get(N, ["maxprocallowed"]) -> rpc:call(N, erlang, system_info, [process_limit]); ++get(_, ["procqueue", title]) -> "Number of processes on the running queue"; ++get(N, ["procqueue"]) -> rpc:call(N, erlang, statistics, [run_queue]); ++get(_, ["uptimehuman", title]) -> "Uptime"; ++get(N, ["uptimehuman"]) -> ++ io_lib:format("~w days ~w hours ~w minutes ~p seconds", ms_to_time(get(N, ["uptime"]))); ++get(_, ["lastrestart", title]) -> "Last restart"; ++get(N, ["lastrestart"]) -> ++ Now = calendar:datetime_to_gregorian_seconds(rpc:call(N, erlang, localtime, [])), ++ UptimeMS = get(N, ["uptime"]), ++ Last_restartS = trunc(Now - (UptimeMS/1000)), ++ Last_restart = calendar:gregorian_seconds_to_datetime(Last_restartS), ++ localtime_to_string(Last_restart); ++ ++get(_, ["plainusers", title]) -> "Plain users"; ++get(_, ["plainusers"]) -> {R, _, _} = get_connectiontype(), R; ++get(_, ["tlsusers", title]) -> "TLS users"; ++get(_, ["tlsusers"]) -> {_, R, _} = get_connectiontype(), R; ++get(_, ["sslusers", title]) -> "SSL users"; ++get(_, ["sslusers"]) -> {_, _, R} = get_connectiontype(), R; ++get(_, ["registeredusers", title]) -> "Registered users"; ++get(N, ["registeredusers"]) -> rpc:call(N, mnesia, table_info, [passwd, size]); ++get(_, ["registeredusers", Host]) -> length(ejabberd_auth:get_vh_registered_users(Host)); ++get(_, ["onlineusers", title]) -> "Online users"; ++get(N, ["onlineusers"]) -> rpc:call(N, mnesia, table_info, [session, size]); ++get(_, ["onlineusers", Host]) -> length(ejabberd_sm:get_vh_session_list(Host)); ++get(_, ["httppollusers", title]) -> "HTTP-Poll users (aprox)"; ++get(N, ["httppollusers"]) -> rpc:call(N, mnesia, table_info, [http_poll, size]); ++get(_, ["httpbindusers", title]) -> "HTTP-Bind users (aprox)"; ++get(N, ["httpbindusers"]) -> rpc:call(N, mnesia, table_info, [http_bind, size]); ++ ++get(_, ["s2sconnections", title]) -> "Outgoing S2S connections"; ++get(_, ["s2sconnections"]) -> length(get_S2SConns()); ++get(_, ["s2sconnections", Host]) -> get_s2sconnections(Host); ++get(_, ["s2sservers", title]) -> "Outgoing S2S servers"; ++get(_, ["s2sservers"]) -> length(lists:usort([element(2, C) || C <- get_S2SConns()])); ++ ++get(_, ["offlinemsg", title]) -> "Offline messages"; ++get(N, ["offlinemsg"]) -> rpc:call(N, mnesia, table_info, [offline_msg, size]); ++get(_, ["offlinemsg", Host]) -> get_offlinemsg(Host); ++get(_, ["totalrosteritems", title]) -> "Total roster items"; ++get(N, ["totalrosteritems"]) -> rpc:call(N, mnesia, table_info, [roster, size]); ++get(_, ["totalrosteritems", Host]) -> get_totalrosteritems(Host); ++ ++get(_, ["meanitemsinroster", title]) -> "Mean items in roster"; ++get(_, ["meanitemsinroster"]) -> get_meanitemsinroster(); ++get(_, ["meanitemsinroster", Host]) -> get_meanitemsinroster(Host); ++ ++get(_, ["totalmucrooms", title]) -> "Total MUC rooms"; ++get(_, ["totalmucrooms"]) -> ets:info(muc_online_room, size); ++get(_, ["totalmucrooms", Host]) -> get_totalmucrooms(Host); ++get(_, ["permmucrooms", title]) -> "Permanent MUC rooms"; ++get(N, ["permmucrooms"]) -> rpc:call(N, mnesia, table_info, [muc_room, size]); ++get(_, ["permmucrooms", Host]) -> get_permmucrooms(Host); ++get(_, ["regmucrooms", title]) -> "Users registered at MUC service"; ++get(N, ["regmucrooms"]) -> rpc:call(N, mnesia, table_info, [muc_registered, size]); ++get(_, ["regmucrooms", Host]) -> get_regmucrooms(Host); ++get(_, ["regpubsubnodes", title]) -> "Registered nodes at Pub/Sub"; ++get(N, ["regpubsubnodes"]) -> rpc:call(N, mnesia, table_info, [pubsub_node, size]); ++get(_, ["vcards", title]) -> "Total vCards published"; ++get(N, ["vcards"]) -> rpc:call(N, mnesia, table_info, [vcard, size]); ++get(_, ["vcards", Host]) -> get_vcards(Host); ++ ++%%get(_, ["ircconns", title]) -> "IRC connections"; ++%%get(_, ["ircconns"]) -> ets:info(irc_connection, size); ++%%get(_, ["ircconns", Host]) -> get_irccons(Host); % This seems to crash for some people ++get(_, ["uptime", title]) -> "Uptime"; ++get(N, ["uptime"]) -> element(1, rpc:call(N, erlang, statistics, [wall_clock])); ++get(_, ["cputime", title]) -> "CPU Time"; ++get(N, ["cputime"]) -> element(1, rpc:call(N, erlang, statistics, [runtime])); ++ ++get(_, ["languages", title]) -> "Languages"; ++get(_, ["languages", Server]) -> get_languages(Server); ++ ++get(_, ["client_os", title]) -> "Client/OS"; ++get(_, ["client_os", Server]) -> get_client_os(Server); ++ ++get(_, ["client_conntype", title]) -> "Client/Connection Type"; ++get(_, ["client_conntype", Server]) -> get_client_conntype(Server); ++ ++get(N, A) -> ++ io:format(" ----- node: '~p', A: '~p'~n", [N, A]), ++ "666". ++ ++%%%================================== ++%%%% get_* ++ ++get_S2SConns() -> ejabberd_s2s:dirty_get_connections(). ++ ++get_tls_drv() -> ++ R = lists:filter( ++ fun(P) -> ++ case erlang:port_info(P, name) of ++ {name, "tls_drv"} -> true; ++ _ -> false ++ end ++ end, erlang:ports()), ++ length(R). ++ ++get_connections(Port) -> ++ R = lists:filter( ++ fun(P) -> ++ case inet:port(P) of ++ {ok, Port} -> true; ++ _ -> false ++ end ++ end, erlang:ports()), ++ length(R). ++ ++get_totalrosteritems(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {_LUser, LServer, _LJID} = R#roster.usj, ++ A2 = case LServer of ++ H -> A+1; ++ _ -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, roster) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++%% Copied from ejabberd_sm.erl ++%%-record(session, {sid, usr, us, priority}). ++ ++%%get_authusers(Host) -> ++%% F = fun() -> ++%% F2 = fun(R, {H, A}) -> ++%% {_LUser, LServer, _LResource} = R#session.usr, ++%% A2 = case LServer of ++%% H -> A+1; ++%% _ -> A ++%% end, ++%% {H, A2} ++%% end, ++%% mnesia:foldl(F2, {Host, 0}, session) ++%% end, ++%% {atomic, {Host, Res}} = mnesia:transaction(F), ++%% Res. ++ ++-record(offline_msg, {us, timestamp, expire, from, to, packet}). ++ ++get_offlinemsg(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {_LUser, LServer} = R#offline_msg.us, ++ A2 = case LServer of ++ H -> A+1; ++ _ -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, offline_msg) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++-record(vcard, {us, vcard}). ++ ++get_vcards(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {_LUser, LServer} = R#vcard.us, ++ A2 = case LServer of ++ H -> A+1; ++ _ -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, vcard) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++get_s2sconnections(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {MyServer, _Server} = R#s2s.fromto, ++ A2 = case MyServer of ++ H -> A+1; ++ _ -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, s2s) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++%%-record(irc_connection, {jid_server_host, pid}). ++ ++%%get_irccons(Host) -> ++%% F2 = fun(R, {H, A}) -> ++%% {From, _Server, _Host} = R#irc_connection.jid_server_host, ++%% A2 = case From#jid.lserver of ++%% H -> A+1; ++%% _ -> A ++%% end, ++%% {H, A2} ++%% end, ++%% {Host, Res} = ets:foldl(F2, {Host, 0}, irc_connection), ++%% Res. ++ ++is_host(Host, Subhost) -> ++ Pos = string:len(Host)-string:len(Subhost)+1, ++ case string:rstr(Host, Subhost) of ++ Pos -> true; ++ _ -> false ++ end. ++ ++-record(muc_online_room, {name_host, pid}). ++ ++get_totalmucrooms(Host) -> ++ F2 = fun(R, {H, A}) -> ++ {_Name, MUCHost} = R#muc_online_room.name_host, ++ A2 = case is_host(MUCHost, H) of ++ true -> A+1; ++ false -> A ++ end, ++ {H, A2} ++ end, ++ {Host, Res} = ets:foldl(F2, {Host, 0}, muc_online_room), ++ Res. ++ ++-record(muc_room, {name_host, opts}). ++ ++get_permmucrooms(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {_Name, MUCHost} = R#muc_room.name_host, ++ A2 = case is_host(MUCHost, H) of ++ true -> A+1; ++ false -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, muc_room) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++-record(muc_registered, {us_host, nick}). ++ ++get_regmucrooms(Host) -> ++ F = fun() -> ++ F2 = fun(R, {H, A}) -> ++ {_User, MUCHost} = R#muc_registered.us_host, ++ A2 = case is_host(MUCHost, H) of ++ true -> A+1; ++ false -> A ++ end, ++ {H, A2} ++ end, ++ mnesia:foldl(F2, {Host, 0}, muc_registered) ++ end, ++ {atomic, {Host, Res}} = mnesia:transaction(F), ++ Res. ++ ++get_stat(Stat) -> ++ Host = case Stat of ++ {_, H} -> H; ++ {_, H, _, _} -> H ++ end, ++ Table = table_name(Host), ++ Res = ets:lookup(Table, Stat), ++ [{_, C}] = Res, ++ C. ++ ++get_stat(Stat, Ims) -> ++ Host = case Stat of ++ {_, H} -> H; ++ {_, H, _, _} -> H ++ end, ++ Table = table_name(Host), ++ Res = ets:lookup(Table, Stat), ++ ets:update_counter(Table, Stat, {2,1,0,0}), ++ [{_, C}] = Res, ++ calc_avg(C, Ims). ++%%C. ++ ++calc_avg(Count, TimeMS) -> ++ TimeMIN = TimeMS/(1000*60), ++ Count/TimeMIN. ++ ++%%%================================== ++%%%% utilities ++ ++get_connectiontype() -> ++ C2 = get_connections(5222) -1, ++ C3 = get_connections(5223) -1, ++ NUplain = C2 + C3 - get_tls_drv(), ++ NUtls = C2 - NUplain, ++ NUssl = C3, ++ {NUplain, NUtls, NUssl}. ++ ++ms_to_time(T) -> ++ DMS = 24*60*60*1000, ++ HMS = 60*60*1000, ++ MMS = 60*1000, ++ SMS = 1000, ++ D = trunc(T/DMS), ++ H = trunc((T - (D*DMS)) / HMS), ++ M = trunc((T - (D*DMS) - (H*HMS)) / MMS), ++ S = trunc((T - (D*DMS) - (H*HMS) - (M*MMS)) / SMS), ++ [D, H, M, S]. ++ ++ ++%% Cuando un usuario conecta, pedirle iq:version a nombre de Host/mod_stats2file ++user_login(U) -> ++ User = U#jid.luser, ++ Host = U#jid.lserver, ++ Resource = U#jid.lresource, ++ ets:update_counter(table_name("server"), {user_login, server}, 1), ++ ets:update_counter(table_name(Host), {user_login, Host}, 1), ++ request_iqversion(User, Host, Resource). ++ ++ ++user_logout_sm(_, JID, _Data) -> ++ user_logout(JID#jid.luser, JID#jid.lserver, JID#jid.lresource, no_status). ++ ++%% cuando un usuario desconecta, buscar en la tabla su JID/USR y quitarlo ++user_logout(User, Host, Resource, _Status) -> ++ TableHost = table_name(Host), ++ TableServer = table_name("server"), ++ ets:update_counter(TableServer, {user_logout, server}, 1), ++ ets:update_counter(TableHost, {user_logout, Host}, 1), ++ ++ JID = jlib:make_jid(User, Host, Resource), ++ case ets:lookup(TableHost, {session, JID}) of ++ [{_, Client_id, OS_id, Lang, ConnType, _Client, _Version, _OS}] -> ++ ets:delete(TableHost, {session, JID}), ++ ets:update_counter(TableHost, {client, Host, Client_id}, -1), ++ ets:update_counter(TableServer, {client, server, Client_id}, -1), ++ ets:update_counter(TableHost, {os, Host, OS_id}, -1), ++ ets:update_counter(TableServer, {os, server, OS_id}, -1), ++ ets:update_counter(TableHost, {conntype, Host, ConnType}, -1), ++ ets:update_counter(TableServer, {conntype, server, ConnType}, -1), ++ update_counter_create(TableHost, {client_os, Host, Client_id, OS_id}, -1), ++ update_counter_create(TableServer, {client_os, server, Client_id, OS_id}, -1), ++ update_counter_create(TableHost, {client_conntype, Host, Client_id, ConnType}, -1), ++ update_counter_create(TableServer, {client_conntype, server, Client_id, ConnType}, -1), ++ update_counter_create(TableHost, {lang, Host, Lang}, -1), ++ update_counter_create(TableServer, {lang, server, Lang}, -1); ++ [] -> ++ ok ++ end. ++ ++request_iqversion(User, Host, Resource) -> ++ From = jlib:make_jid("", Host, atom_to_list(?MODULE)), ++ FromStr = jlib:jid_to_string(From), ++ To = jlib:make_jid(User, Host, Resource), ++ ToStr = jlib:jid_to_string(To), ++ Packet = {xmlelement,"iq", ++ [{"from",FromStr}, {"to",ToStr}, {"type","get"}, {"xml:lang","es"}], ++ [{xmlcdata,"\n"}, {xmlcdata," "}, ++ {xmlelement, "query", ++ [{"xmlns","jabber:iq:version"}], []}, {xmlcdata,"\n"}]}, ++ ejabberd_local:route(From, To, Packet). ++ ++%% cuando el virtualJID recibe una respuesta iqversion, ++%% almacenar su JID/USR + client + OS en una tabla ++received_response(From, _To, El) -> ++ try received_response(From, El) ++ catch ++ _:_ -> ok ++ end. ++received_response(From, {xmlelement, "iq", Attrs, Elc}) -> ++ User = From#jid.luser, ++ Host = From#jid.lserver, ++ Resource = From#jid.lresource, ++ ++ "result" = xml:get_attr_s("type", Attrs), ++ Lang = case xml:get_attr_s("xml:lang", Attrs) of ++ [] -> "unknown"; ++ L -> L ++ end, ++ TableHost = table_name(Host), ++ TableServer = table_name("server"), ++ update_counter_create(TableHost, {lang, Host, Lang}, 1), ++ update_counter_create(TableServer, {lang, server, Lang}, 1), ++ ++ [El] = xml:remove_cdata(Elc), ++ {xmlelement, _, Attrs2, _Els2} = El, ++ ?NS_VERSION = xml:get_attr_s("xmlns", Attrs2), ++ ++ Client = get_tag_cdata_subtag(El, "name"), ++ Version = get_tag_cdata_subtag(El, "version"), ++ OS = get_tag_cdata_subtag(El, "os"), ++ {Client_id, OS_id} = identify(Client, OS), ++ ++ ConnType = get_connection_type(User, Host, Resource), ++ ++ TableHost = table_name(Host), ++ TableServer = table_name("server"), ++ ets:update_counter(TableHost, {client, Host, Client_id}, 1), ++ ets:update_counter(TableServer, {client, server, Client_id}, 1), ++ ets:update_counter(TableHost, {os, Host, OS_id}, 1), ++ ets:update_counter(TableServer, {os, server, OS_id}, 1), ++ ets:update_counter(TableHost, {conntype, Host, ConnType}, 1), ++ ets:update_counter(TableServer, {conntype, server, ConnType}, 1), ++ update_counter_create(TableHost, {client_os, Host, Client_id, OS_id}, 1), ++ update_counter_create(TableServer, {client_os, server, Client_id, OS_id}, 1), ++ update_counter_create(TableHost, {client_conntype, Host, Client_id, ConnType}, 1), ++ update_counter_create(TableServer, {client_conntype, server, Client_id, ConnType}, 1), ++ ++ JID = jlib:make_jid(User, Host, Resource), ++ ets:insert(TableHost, {{session, JID}, Client_id, OS_id, Lang, ConnType, Client, Version, OS}). ++ ++get_connection_type(User, Host, Resource) -> ++ [_Node, {conn, Conn}, _IP] = ejabberd_sm:get_user_info(User, Host, Resource), ++ Conn. ++ ++update_counter_create(Table, Element, C) -> ++ case ets:lookup(Table, Element) of ++ [] -> ets:insert(Table, {Element, 1}); ++ _ -> ets:update_counter(Table, Element, C) ++ end. ++ ++get_tag_cdata_subtag(E, T) -> ++ E2 = xml:get_subtag(E, T), ++ case E2 of ++ false -> "unknown"; ++ _ -> xml:get_tag_cdata(E2) ++ end. ++ ++list_elem(Type, id) -> ++ {_, Ids} = lists:unzip(list_elem(Type, full)), ++ Ids; ++list_elem(clients, full) -> ++ [ ++ {"Pidgin", pidgin}, ++ {"pidgin", pidgin}, ++ {"gaim", gaim}, ++ {"Gajim", gajim}, ++ {"Tkabber", tkabber}, ++ {"Psi", psi}, ++ {"Adium", adium}, ++ {"Pandion", pandion}, ++ {"Kopete", kopete}, ++ {"Exodus", exodus}, ++ {"libgaim", libgaim}, ++ {"JBother", jbother}, ++ {"iChat", ichat}, ++ {"Miranda", miranda}, ++ {"Trillian", trillian}, ++ {"QIP Infium", qipinfium}, ++ {"JAJC", jajc}, ++ {"Coccinella", coccinella}, ++ {"Gabber", gabber}, ++ {"BitlBee", bitlbee}, ++ {"jabber.el", jabberel}, ++ {"unknown", unknown} ++ ]; ++list_elem(conntypes, full) -> ++ [ ++ {"c2s", c2s}, ++ {"c2s_tls", c2s_tls}, ++ {"c2s_compressed", c2s_compressed}, ++ {"http_poll", http_poll}, ++ {"http_bind", http_bind}, ++ {"unknown", unknown} ++ ]; ++list_elem(oss, full) -> ++ [ ++ {"Linux", linux}, ++ {"Win", windows}, ++ {"Gentoo", linux}, ++ {"Mac", mac}, ++ {"BSD", bsd}, ++ {"SunOS", linux}, ++ {"Debian", linux}, ++ {"Ubuntu", linux}, ++ {"unknown", unknown} ++ ]. ++ ++identify(Client, OS) -> ++ Res = {try_match(Client, list_elem(clients, full)), try_match(OS, list_elem(oss, full))}, ++ case Res of ++ {libgaim, mac} -> {adium, mac}; ++ {adium, unknown} -> {adium, mac}; ++ {qipinfium, unknown} -> {qipinfium, windows}; ++ _ -> Res ++ end. ++ ++try_match(_E, []) -> unknown; ++try_match(E, [{Str, Id} | L]) -> ++ case string:str(E, Str) of ++ 0 -> try_match(E, L); ++ _ -> Id ++ end. ++ ++get_client_os(Server) -> ++ CO1 = ets:match(table_name(Server), {{client_os, Server, '$1', '$2'}, '$3'}), ++ CO2 = lists:map( ++ fun([Cl, Os, A3]) -> ++ {lists:flatten([atom_to_list(Cl), "/", atom_to_list(Os)]), A3} ++ end, ++ CO1 ++ ), ++ lists:keysort(1, CO2). ++ ++get_client_conntype(Server) -> ++ CO1 = ets:match(table_name(Server), {{client_conntype, Server, '$1', '$2'}, '$3'}), ++ CO2 = lists:map( ++ fun([Cl, Os, A3]) -> ++ {lists:flatten([atom_to_list(Cl), "/", atom_to_list(Os)]), A3} ++ end, ++ CO1 ++ ), ++ lists:keysort(1, CO2). ++ ++get_languages(Server) -> ++ L1 = ets:match(table_name(Server), {{lang, Server, '$1'}, '$2'}), ++ L2 = lists:map( ++ fun([La, C]) -> ++ {La, C} ++ end, ++ L1 ++ ), ++ lists:keysort(1, L2). ++ ++get_meanitemsinroster() -> ++ get_meanitemsinroster2(getl("totalrosteritems"), getl("registeredusers")). ++get_meanitemsinroster(Host) -> ++ get_meanitemsinroster2(getl("totalrosteritems", Host), getl("registeredusers", Host)). ++get_meanitemsinroster2(Items, Users) -> ++ case Users of ++ 0 -> 0; ++ _ -> Items/Users ++ end. ++ ++localtime_to_string({{Y, Mo, D},{H, Mi, S}}) -> ++ lists:concat([H, ":", Mi, ":", S, " ", D, "/", Mo, "/", Y]). ++ ++%% cuando toque mostrar estadisticas ++%%get_iqversion() -> ++%% contar en la tabla cuantos tienen cliente: *psi* ++%%buscar en la tabla iqversion ++%%ok. ++ ++ ++%%%================================== ++%%%% Web Admin Menu ++ ++web_menu_main(Acc, Lang) -> ++ Acc ++ [{"statsdx", ?T("Statistics Dx")}]. ++ ++web_menu_node(Acc, _Node, Lang) -> ++ Acc ++ [{"statsdx", ?T("Statistics Dx")}]. ++ ++web_menu_host(Acc, _Host, Lang) -> ++ Acc ++ [{"statsdx", ?T("Statistics Dx")}]. ++ ++%%%================================== ++%%%% Web Admin Page ++ ++web_page_main(_, #request{path=["statsdx"], lang = Lang} = _Request) -> ++ Res = [?XC("h1", ?T("Statistics")++" Dx"), ++ ?XC("h3", "Accounts"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "registeredusers") ++ ]) ++ ]), ++ ?XC("h3", "Roster"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "totalrosteritems"), ++ do_stat(global, Lang, "meanitemsinroster") ++ ]) ++ ]), ++ ?XC("h3", "Users"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "onlineusers"), ++ do_stat(global, Lang, "offlinemsg"), ++ do_stat(global, Lang, "vcards") ++ ]) ++ ]), ++ ?XC("h3", "MUC"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "totalmucrooms"), ++ do_stat(global, Lang, "permmucrooms"), ++ do_stat(global, Lang, "regmucrooms") ++ ]) ++ ]), ++ ?XC("h3", "Pub/Sub"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "regpubsubnodes") ++ ]) ++ ]), ++ %%?XC("h3", "IRC"), ++ %%?XAE("table", [], ++ %% [?XE("tbody", [ ++ %% do_stat(global, Lang, "ircconns") ++ %% ]) ++ %%]), ++ %%?XC("h3", "Ratios"), ++ %%?XAE("table", [], ++ %% [?XE("tbody", [ ++ %% ]) ++ %% ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client", server) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("os")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "os", server) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client") ++ "/" ++ get_stat_n("os")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client_os", server) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("conntype")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "conntype", server) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client") ++ "/" ++ get_stat_n("conntype")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client_conntype", server) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("languages")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "languages", server) ++ ) ++ ]) ++ ], ++ {stop, Res}; ++web_page_main(_, #request{path=["statsdx" | FilterURL], q = Q, lang = Lang} = _Request) -> ++ Filter = parse_url_filter(FilterURL), ++ Sort_query = get_sort_query(Q), ++ Res = [?XC("h1", ?T("Statistics")++" Dx"), ++ ?XC("h2", "Sessions with: "++ io_lib:format("~p", [Filter])), ++ ?XE("table", ++ [ ++ ?XE("thead", [?XE("tr", make_sessions_table_tr(Lang) )]), ++ ?XE("tbody", do_sessions_table(global, Lang, Filter, Sort_query, server)) ++ ]) ++ ], ++ {stop, Res}; ++web_page_main(Acc, _) -> Acc. ++ ++%% Code copied from mod_muc_admin.erl ++%% Returns: {normal | reverse, Integer} ++get_sort_query(Q) -> ++ case catch get_sort_query2(Q) of ++ {ok, Res} -> Res; ++ _ -> {normal, 1} ++ end. ++get_sort_query2(Q) -> ++ {value, {_, String}} = lists:keysearch("sort", 1, Q), ++ Integer = list_to_integer(String), ++ case Integer >= 0 of ++ true -> {ok, {normal, Integer}}; ++ false -> {ok, {reverse, abs(Integer)}} ++ end. ++make_sessions_table_tr(Lang) -> ++ Titles = ["Jabber ID", ++ "Client ID", ++ "OS ID", ++ "Lang", ++ "Connection", ++ "Client", ++ "Version", ++ "OS"], ++ {Titles_TR, _} = ++ lists:mapfoldl( ++ fun(Title, Num_column) -> ++ NCS = integer_to_list(Num_column), ++ TD = ?XE("td", [?CT(Title), ++ ?BR, ++ ?ACT("?sort="++NCS, "<"), ++ ?C(" "), ++ ?ACT("?sort=-"++NCS, ">")]), ++ {TD, Num_column+1} ++ end, ++ 1, ++ Titles), ++ Titles_TR. ++ ++%% @spec (Filter::string()) -> [{Class::string(), Type::string()}] ++parse_url_filter(FilterURL) -> ++ [List] = string:tokens(FilterURL, "/"), ++ parse_url_filter(List, []). ++parse_url_filter([Class, Type | List], Res) -> ++ parse_url_filter(List, Res ++ [{Class, Type}]); ++parse_url_filter(_, Res) -> ++ Res. ++ ++ ++web_page_node(_, Node, ["statsdx"], _Query, Lang) -> ++ TransactionsCommited = ++ rpc:call(Node, mnesia, system_info, [transaction_commits]), ++ TransactionsAborted = ++ rpc:call(Node, mnesia, system_info, [transaction_failures]), ++ TransactionsRestarted = ++ rpc:call(Node, mnesia, system_info, [transaction_restarts]), ++ TransactionsLogged = ++ rpc:call(Node, mnesia, system_info, [transaction_log_writes]), ++ ++ Res = ++ [?XC("h1", io_lib:format(?T("~p statistics"), [Node])), ++ ?XC("h3", "Connections"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "onlineusers"), ++ do_stat(Node, Lang, "httppollusers"), ++ do_stat(Node, Lang, "httpbindusers"), ++ do_stat(Node, Lang, "s2sconnections"), ++ do_stat(Node, Lang, "s2sservers") ++ ]) ++ ]), ++ ?XC("h3", "ejabberd"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(Node, Lang, "ejabberdversion") ++ ]) ++ ]), ++ ?XC("h3", "Erlang"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(Node, Lang, "operatingsystem"), ++ do_stat(Node, Lang, "erlangmachine"), ++ do_stat(Node, Lang, "erlangmachinetarget"), ++ do_stat(Node, Lang, "maxprocallowed"), ++ do_stat(Node, Lang, "procqueue"), ++ do_stat(Node, Lang, "totalerlproc") ++ ]) ++ ]), ++ ?XC("h3", "Times"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(Node, Lang, "uptime"), ++ do_stat(Node, Lang, "uptimehuman"), ++ do_stat(Node, Lang, "lastrestart"), ++ do_stat(Node, Lang, "cputime") ++ ]) ++ ]), ++ ?XC("h3", "CPU"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(Node, Lang, "cpu_avg1"), ++ do_stat(Node, Lang, "cpu_avg5"), ++ do_stat(Node, Lang, "cpu_avg15"), ++ do_stat(Node, Lang, "cpu_nprocs")%, ++ %%do_stat(Node, Lang, "cpu_util_user"), ++ %%do_stat(Node, Lang, "cpu_nice_user"), ++ %%do_stat(Node, Lang, "cpu_kernel"), ++ %%do_stat(Node, Lang, "cpu_idle"), ++ %%do_stat(Node, Lang, "cpu_wait") ++ ]) ++ ]), ++ %%?XC("h3", "RAM"), ++ %%?XAE("table", [], ++ %% [?XE("tbody", [ ++ %% do_stat(Node, Lang, "memsup_system"), ++ %% do_stat(Node, Lang, "memsup_free"), ++ %% do_stat(Node, Lang, "reductions") ++ %%]) ++ %%]), ++ ?XC("h3", "Memory (bytes)"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(Node, Lang, "memory_total"), ++ do_stat(Node, Lang, "memory_processes"), ++ do_stat(Node, Lang, "memory_processes_used"), ++ do_stat(Node, Lang, "memory_system"), ++ do_stat(Node, Lang, "memory_atom"), ++ do_stat(Node, Lang, "memory_atom_used"), ++ do_stat(Node, Lang, "memory_binary"), ++ do_stat(Node, Lang, "memory_code"), ++ do_stat(Node, Lang, "memory_ets") ++ ]) ++ ]), ++ ?XC("h3", "Database"), ++ ?XAE("table", [], ++ [?XE("tbody", ++ [ ++ ?XE("tr", [?XCT("td", "Transactions commited"), ++ ?XAC("td", [{"class", "alignright"}], ++ integer_to_list(TransactionsCommited))]), ++ ?XE("tr", [?XCT("td", "Transactions aborted"), ++ ?XAC("td", [{"class", "alignright"}], ++ integer_to_list(TransactionsAborted))]), ++ ?XE("tr", [?XCT("td", "Transactions restarted"), ++ ?XAC("td", [{"class", "alignright"}], ++ integer_to_list(TransactionsRestarted))]), ++ ?XE("tr", [?XCT("td", "Transactions logged"), ++ ?XAC("td", [{"class", "alignright"}], ++ integer_to_list(TransactionsLogged))]) ++ ]) ++ ])], ++ {stop, Res}; ++web_page_node(Acc, _, _, _, _) -> Acc. ++ ++web_page_host(_, Host, ++ #request{path = ["statsdx"], ++ lang = Lang} = _Request) -> ++ Res = [?XC("h1", ?T("Statistics")++" Dx"), ++ ?XC("h2", Host), ++ ?XC("h3", "Accounts"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "registeredusers", Host) ++ ]) ++ ]), ++ ?XC("h3", "Roster"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "totalrosteritems", Host) ++ %%get_meanitemsinroster2(TotalRosterItems, RegisteredUsers) ++ ]) ++ ]), ++ ?XC("h3", "Users"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "onlineusers", Host) ++ %%do_stat(global, Lang, "offlinemsg", Host), %% This make take a lot of time ++ %%do_stat(global, Lang, "vcards", Host) %% This make take a lot of time ++ ]) ++ ]), ++ ?XC("h3", "Connections"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "s2sconnections", Host) ++ ]) ++ ]), ++ ?XC("h3", "MUC"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "totalmucrooms", Host), ++ do_stat(global, Lang, "permmucrooms", Host), ++ do_stat(global, Lang, "regmucrooms", Host) ++ ]) ++ ]), ++ %%?XC("h3", "IRC"), ++ %%?XAE("table", [], ++ %% [?XE("tbody", [ ++ %% do_stat(global, Lang, "ircconns", Host) ++ %% ]) ++ %%]), ++ %%?XC("h3", "Pub/Sub"), ++ %%?XAE("table", [], ++ %% [?XE("tbody", [ ++ %% do_stat(global, Lang, "regpubsubnodes", Host) ++ %% ]) ++ %%]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client", Host) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("os")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "os", Host) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client") ++ "/" ++ get_stat_n("os")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client_os", Host) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("conntype")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "conntype", Host) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("client") ++ "/" ++ get_stat_n("conntype")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "client_conntype", Host) ++ ) ++ ]), ++ ?XC("h3", "Sessions: " ++ get_stat_n("languages")), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_stat_table(global, Lang, "languages", Host) ++ ) ++ ]), ++ ?XC("h3", "Ratios"), ++ ?XAE("table", [], ++ [?XE("tbody", [ ++ do_stat(global, Lang, "user_login", Host), ++ do_stat(global, Lang, "user_logout", Host), ++ do_stat(global, Lang, "remove_user", Host), ++ do_stat(global, Lang, {send, iq, in}, Host), ++ do_stat(global, Lang, {send, iq, out}, Host), ++ do_stat(global, Lang, {send, message, in}, Host), ++ do_stat(global, Lang, {send, message, out}, Host), ++ do_stat(global, Lang, {send, presence, in}, Host), ++ do_stat(global, Lang, {send, presence, out}, Host), ++ do_stat(global, Lang, {recv, iq, in}, Host), ++ do_stat(global, Lang, {recv, iq, out}, Host), ++ do_stat(global, Lang, {recv, message, in}, Host), ++ do_stat(global, Lang, {recv, message, out}, Host), ++ do_stat(global, Lang, {recv, presence, in}, Host), ++ do_stat(global, Lang, {recv, presence, out}, Host) ++ ]) ++ ]) ++ ], ++ {stop, Res}; ++web_page_host(_, Host, #request{path=["statsdx" | FilterURL], q = Q, ++ lang = Lang} = _Request) -> ++ Filter = parse_url_filter(FilterURL), ++ Sort_query = get_sort_query(Q), ++ Res = [?XC("h1", ?T("Statistics")++" Dx"), ++ ?XC("h2", "Sessions with: "++ io_lib:format("~p", [Filter])), ++ ?XAE("table", [], ++ [?XE("tbody", ++ do_sessions_table(global, Lang, Filter, Sort_query, Host) ++ ) ++ ]) ++ ], ++ {stop, Res}; ++web_page_host(Acc, _, _) -> Acc. ++ ++ ++%%%================================== ++%%%% Web Admin Utils ++ ++do_table_element(Lang, L, StatLink, N) -> ++ ?XE("tr", [ ++ case StatLink of ++ no_link -> ?XCT("td", L); ++ _ -> ?XE("td", [?AC(make_url(StatLink, L), L)]) ++ end, ++ ?XAC("td", [{"class", "alignright"}], ++ N) ++ ]). ++ ++make_url(StatLink, L) -> ++ List = case string:tokens(StatLink, "_") of ++ [Stat] -> ++ [Stat, L]; ++ [Stat1, Stat2] -> ++ [L1, L2] = string:tokens(L, "/"), ++ [Stat1, L1, Stat2, L2] ++ end, ++ string:join(List, "/"). ++ ++do_stat_table(global, Lang, Stat, Host) -> ++ Os = mod_statsdx:get_statistic(global, [Stat, Host]), ++ lists:map( ++ fun({L, N}) -> ++ do_table_element(Lang, L, Stat, io_lib:format("~p", [N])) ++ end, ++ lists:reverse(lists:keysort(2, Os)) ++ ). ++ ++do_sessions_table(_Node, _Lang, Filter, {Sort_direction, Sort_column}, Host) -> ++ Sessions = get_sessions_filtered(Filter, Host), ++ SessionsSorted = sort_sessions(Sort_direction, Sort_column, Sessions), ++ lists:map( ++ fun( {{session, JID}, Client_id, OS_id, Lang, ConnType, Client, Version, OS} ) -> ++ User = JID#jid.luser, ++ Server = JID#jid.lserver, ++ UserURL = "/admin/server/" ++ Server ++ "/user/" ++ User ++ "/", ++ ?XE("tr", [ ++ ?XE("td", [?AC(UserURL, jlib:jid_to_string(JID))]), ++ ?XCT("td", atom_to_list(Client_id)), ++ ?XCT("td", atom_to_list(OS_id)), ++ ?XCT("td", Lang), ++ ?XCT("td", atom_to_list(ConnType)), ++ ?XCT("td", Client), ++ ?XCT("td", Version), ++ ?XCT("td", OS) ++ ]) ++ end, ++ SessionsSorted ++ ). ++ ++%% Code copied from mod_muc_admin.erl ++sort_sessions(Direction, Column, Rooms) -> ++ Rooms2 = lists:keysort(Column, Rooms), ++ case Direction of ++ normal -> Rooms2; ++ reverse -> lists:reverse(Rooms2) ++ end. ++ ++get_sessions_filtered(Filter, server) -> ++ lists:foldl( ++ fun(Host, Res) -> ++ try get_sessions_filtered(Filter, Host) of ++ List when is_list(List) -> List ++ Res ++ catch ++ _:_ -> Res ++ end ++ end, ++ [], ++ ?MYHOSTS); ++get_sessions_filtered(Filter, Host) -> ++ Match = case Filter of ++ [{"client", Client}] -> {{session, '$1'}, list_to_atom(Client), '$2', '$3', '$4', '$5', '$6', '$7'}; ++ [{"os", OS}] -> {{session, '$1'}, '$2', list_to_atom(OS), '$3', '$4', '$5', '$6', '$7'}; ++ [{"conntype", ConnType}] -> {{session, '$1'}, '$2', '$3', '$4', list_to_atom(ConnType), '$5', '$6', '$7'}; ++ [{"languages", Lang}] -> {{session, '$1'}, '$2', '$3', Lang, '$4', '$5', '$6', '$7'}; ++ [{"client", Client}, {"os", OS}] -> {{session, '$1'}, list_to_atom(Client), list_to_atom(OS), '$3', '$4', '$5', '$6', '$7'}; ++ [{"client", Client}, {"conntype", ConnType}] -> {{session, '$1'}, list_to_atom(Client), '$2', '$3', list_to_atom(ConnType), '$5', '$6', '$7'}; ++ _ -> {{session, '$1'}, '$2', '$3', '$4', '$5'} ++ end, ++ ets:match_object(table_name(Host), Match). ++ ++do_stat(Node, Lang, Stat) -> ++ ?XE("tr", [ ++ ?XCT("td", get_stat_n(Stat)), ++ ?XAC("td", [{"class", "alignright"}], ++ get_stat_v(Node, [Stat]))]). ++ ++do_stat(Node, Lang, Stat, Host) -> ++ %%[Res] = get_stat_v(Node, [Stat, Host]), ++ %%do_table_element(Lang, get_stat_n(Stat), Res). ++ do_table_element(Lang, get_stat_n(Stat), no_link, get_stat_v(Node, [Stat, Host])). ++ ++%% Get a stat name ++get_stat_n(Stat) -> ++ mod_statsdx:get_statistic(foo, [Stat, title]). ++%% Get a stat value ++get_stat_v(Node, Stat) -> get_stat_v2(mod_statsdx:get_statistic(Node, Stat)). ++get_stat_v2(Value) when is_list(Value) -> Value; ++get_stat_v2(Value) when is_float(Value) -> io_lib:format("~.4f", [Value]); ++get_stat_v2(Value) when is_integer(Value) -> ++ [Str] = io_lib:format("~p", [Value]), ++ pretty_string_int(Str); ++get_stat_v2(Value) -> io_lib:format("~p", [Value]). ++ ++%% Transform "1234567890" into "1,234,567,890" ++pretty_string_int(String) -> ++ {_, Result} = lists:foldl( ++ fun(NewNumber, {3, Result}) -> ++ {1, [NewNumber, $, | Result]}; ++ (NewNumber, {CountAcc, Result}) -> ++ {CountAcc+1, [NewNumber | Result]} ++ end, ++ {0, ""}, ++ lists:reverse(String)), ++ Result. ++ ++%%%================================== ++%%%% Commands ++ ++commands() -> ++ [ ++ #ejabberd_commands{name = getstatsdx, tags = [stats], ++ desc = "Get statistical value.", ++ module = ?MODULE, function = getstatsdx, ++ args = [{name, string}], ++ result = {stat, integer}}, ++ #ejabberd_commands{name = getstatsdx_host, tags = [stats], ++ desc = "Get statistical value for this host.", ++ module = ?MODULE, function = getstatsdx, ++ args = [{name, string}, {host, string}], ++ result = {stat, integer}} ++ ]. ++ ++getstatsdx(Name) -> ++ get_statistic(global, [Name]). ++ ++getstatsdx(Name, Host) -> ++ get_statistic(global, [Name, Host]). ++ ++%%%================================== ++ ++%%% vim: set foldmethod=marker foldmarker=%%%%,%%%=: diff --git a/net-im/ejabberd/files/ejabberd-2.confd b/net-im/ejabberd/files/ejabberd-2.confd new file mode 100644 index 0000000..ce9211b --- /dev/null +++ b/net-im/ejabberd/files/ejabberd-2.confd @@ -0,0 +1,23 @@ +# Copyright 1999-2008 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Header: /var/cvsroot/gentoo-x86/net-im/ejabberd/files/ejabberd-2.0.2.confd,v 1.1 2008/08/03 16:19:05 caleb Exp $ + +# Name of your ejabberd node. Used by ejabberdctl to determine which +# node to communicate with. +EJABBERD_NODE="ejabberd@`hostname -s`" + +# Max number of open network connections. Default is 1024. Increasing +# this will slightly increase memory usage. +#ERL_MAX_PORTS=1024 + +# Return memory to the system after using it, instead of keeping it +# allocated for future use. Decreases the memory required by ejabberd, +# but makes it run slower. Default is unset, set to any value to +# activate. +#ERL_FULLSWEEP_AFTER=0 + +# set to 1, "true" or "yes" if you have a symmetric-multi-processor +# default is non smp +#HAVE_SMP=0 + + diff --git a/net-im/ejabberd/files/ejabberd-2.initd b/net-im/ejabberd/files/ejabberd-2.initd new file mode 100644 index 0000000..329001a --- /dev/null +++ b/net-im/ejabberd/files/ejabberd-2.initd @@ -0,0 +1,54 @@ +#!/sbin/runscript +# Copyright 1999-2008 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Header: /var/cvsroot/gentoo-x86/net-im/ejabberd/files/ejabberd-2.0.2.initd,v 1.1 2008/08/03 16:19:05 caleb Exp $ + +opts="${opts} reload" + +depend() { + use dns + need net + provide jabber-server +} + +checkconfig() { + if [ ! -e /etc/jabber/ejabberd.cfg ] ; then + eerror "You need a /etc/jabber/ejabberd.cfg file to run ejabberd" + return 1 + fi +} + +start() { + checkconfig || return 1 + ebegin "Starting ejabberd" + # the process name of beam is different depending whether smp is used. + # set it explicitly so start-stop-daemon works + case "$HAVE_SMP" in + "1"|"true"|"yes") + BEAMNAME="beam.smp" + SMPOPT="enable" + ;; + *) + BEAMNAME="beam" + SMPOPT="disable" + ;; + esac + cd /var/lib/ejabberd + start-stop-daemon --start --quiet --chuid jabber:jabber \ + --name $BEAMNAME \ + --exec /usr/sbin/ejabberd -- -detached -noinput -smp $SMPOPT + eend $? +} + +stop() { + ebegin "Stopping ejabberd" + /usr/sbin/ejabberdctl stop + eend $? +} + +reload() { + ebegin "Reloading ejabberd" + /usr/sbin/ejabberdctl reopen-log + eend $? +} + diff --git a/net-im/ejabberd/files/ejabberd-wrapper-2.template b/net-im/ejabberd/files/ejabberd-wrapper-2.template new file mode 100644 index 0000000..89f3ff4 --- /dev/null +++ b/net-im/ejabberd/files/ejabberd-wrapper-2.template @@ -0,0 +1,49 @@ +#!/bin/sh + +[ -f /etc/conf.d/ejabberd ] && . /etc/conf.d/ejabberd + +# provide some default configuration +ERL=/usr/bin/erl +CONFIG=/etc/jabber/ejabberd.cfg +INETRC=/etc/jabber/inetrc +LOG_PATH=/var/log/jabber/ejabberd.log +SASL_LOG=/var/log/jabber/sasl.log +SPOOL=/var/spool/jabber + +ARGS= +while [ $# -ne 0 ] ; do + PARAM=$1 + shift + case $PARAM in + --) break ;; + --node) EJABBERD_NODE=$1; shift ;; + --config) CONFIG=$1 ; shift ;; + --log) LOG_PATH=$1 ; shift ;; + --sasl-log) SASL_LOG=$1 ; shift ;; + --spool) SPOOL=$1 ; shift ;; + *) ARGS="$ARGS $PARAM" ;; + esac +done + +if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%.*}" ] ; then + SNAME=-sname +else + SNAME=-name +fi + +# export ejabberd configuration environment variables +export HOME=/var/run/jabber +export EJABBERD_EBIN=/usr/@libdir@/erlang/lib/ejabberd-@version@/ebin +export EJABBERD_MSGS_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/msgs +export EJABBERD_SO_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/lib +export EJABBERD_LOG_PATH=$LOG_PATH +export EJABBERD_CONFIG_PATH=$CONFIG + +exec $ERL $SNAME $EJABBERD_NODE \ + -s ejabberd \ + -kernel inetrc \"$INETRC\" \ + -sasl sasl_error_logger \{file,\"$SASL_LOG\"\} \ + -mnesia dir \"$SPOOL\" \ + $ERL_OPTIONS $ARGS "$@" + + diff --git a/net-im/ejabberd/files/ejabberd-wrapper-3.template b/net-im/ejabberd/files/ejabberd-wrapper-3.template new file mode 100644 index 0000000..146ef52 --- /dev/null +++ b/net-im/ejabberd/files/ejabberd-wrapper-3.template @@ -0,0 +1,50 @@ +#!/bin/sh + +[ -f /etc/conf.d/ejabberd ] && . /etc/conf.d/ejabberd + +# provide some default configuration +ERL=/usr/bin/erl +CONFIG=/etc/jabber/ejabberd.cfg +INETRC=/etc/jabber/inetrc +LOG_PATH=/var/log/jabber/ejabberd.log +SASL_LOG=/var/log/jabber/erlang.log +SPOOL=/var/spool/jabber + +ARGS= +while [ $# -ne 0 ] ; do + PARAM=$1 + shift + case $PARAM in + --) break ;; + --node) EJABBERD_NODE=$1; shift ;; + --config) CONFIG=$1 ; shift ;; + --log) LOG_PATH=$1 ; shift ;; + --sasl-log) SASL_LOG=$1 ; shift ;; + --spool) SPOOL=$1 ; shift ;; + *) ARGS="$ARGS $PARAM" ;; + esac +done + +if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%.*}" ] ; then + SNAME=-sname +else + SNAME=-name +fi + +# export ejabberd configuration environment variables +export HOME=/var/run/jabber +export EJABBERD_EBIN=/usr/@libdir@/erlang/lib/ejabberd-@version@/ebin +export EJABBERD_MSGS_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/msgs +export EJABBERD_SO_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/lib +export EJABBERD_DOC_PATH=/usr/share/doc/@doc@/html +export EJABBERD_LOG_PATH=$LOG_PATH +export EJABBERD_CONFIG_PATH=$CONFIG + +exec $ERL $SNAME $EJABBERD_NODE \ + -s ejabberd \ + -kernel inetrc \"$INETRC\" \ + -sasl sasl_error_logger \{file,\"$SASL_LOG\"\} \ + -mnesia dir \"$SPOOL\" \ + $ERL_OPTIONS $ARGS "$@" + + diff --git a/net-im/ejabberd/files/ejabberd-wrapper.template b/net-im/ejabberd/files/ejabberd-wrapper.template new file mode 100644 index 0000000..9a0ffe1 --- /dev/null +++ b/net-im/ejabberd/files/ejabberd-wrapper.template @@ -0,0 +1,49 @@ +#!/bin/sh + +[ -f /etc/conf.d/ejabberd ] && . /etc/conf.d/ejabberd + +# provide some default configuration +ERL=/usr/bin/erl +CONFIG=/etc/jabber/ejabberd.cfg +INETRC=/etc/jabber/inetrc +LOG_PATH=/var/log/jabber/ejabberd.log +SASL_LOG=/var/log/jabber/sasl.log +SPOOL=/var/spool/jabber + +ARGS= +while [ $# -ne 0 ] ; do + PARAM=$1 + shift + case $PARAM in + --) break ;; + --node) EJABBERD_NODE=$1; shift ;; + --config) CONFIG=$1 ; shift ;; + --log) LOG_PATH=$1 ; shift ;; + --sasl-log) SASL_LOG=$1 ; shift ;; + --spool) SPOOL=$1 ; shift ;; + *) ARGS="$ARGS $PARAM" ;; + esac +done + +if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%.*}" ] ; then + SNAME=-sname +else + SNAME=-name +fi + +# export ejabberd configuration environment variables +export HOME=/var/run/jabber +export EJABBERD_EBIN=/usr/@libdir@/erlang/lib/ejabberd-@version@/ebin +export EJABBERD_MSGS_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/msgs +export EJABBERD_SO_PATH=/usr/@libdir@/erlang/lib/ejabberd-@version@/priv/lib +export EJABBERD_LOG_PATH=$LOG_PATH +export EJABBERD_CONFIG_PATH=$CONFIG + +exec $ERL $SNAME $EJABBERD_NODE \ + -s ejabberd +K true \ + -kernel inetrc \"$INETRC\" \ + -sasl sasl_error_logger \{file,\"$SASL_LOG\"\} \ + -mnesia dir \"$SPOOL\" \ + $ERL_OPTIONS $ARGS "$@" + + diff --git a/net-im/ejabberd/files/ejabberdctl b/net-im/ejabberd/files/ejabberdctl new file mode 100644 index 0000000..a3a1824 --- /dev/null +++ b/net-im/ejabberd/files/ejabberdctl @@ -0,0 +1,8 @@ +#!/bin/sh + +exec env HOME=/var/run/ejabberd \ + erl -pa /var/lib/ejabberd/ebin \ + -noinput \ + -sname ejabberdctl \ + -s ejabberd_ctl \ + -extra $@ diff --git a/net-im/ejabberd/files/ejabberdctl-wrapper-2.template b/net-im/ejabberd/files/ejabberdctl-wrapper-2.template new file mode 100644 index 0000000..6443678 --- /dev/null +++ b/net-im/ejabberd/files/ejabberdctl-wrapper-2.template @@ -0,0 +1,30 @@ +#!/bin/sh + +[ -f /etc/conf.d/ejabberd ] && . /etc/conf.d/ejabberd + +if [ -r /var/run/jabber/.erlang.cookie ] ; then + HOME=/var/run/jabber + export HOME +fi + +ERL=/usr/bin/erl + +if [ $# -ne 0 ] ; then + case $1 in + --node) shift ; EJABBERD_NODE=$1 ; shift ;; + esac +fi + +if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%.*}" ] ; then + SNAME=-sname +else + SNAME=-name +fi + +exec $ERL $SNAME ejabberdctl \ + -pa /usr/@libdir@/erlang/lib/ejabberd-@version@/ebin \ + -s ejabberd_ctl \ + -noinput \ + -extra $EJABBERD_NODE "$@" + + diff --git a/net-im/ejabberd/files/ejabberdctl-wrapper-3.template b/net-im/ejabberd/files/ejabberdctl-wrapper-3.template new file mode 100644 index 0000000..05b67d8 --- /dev/null +++ b/net-im/ejabberd/files/ejabberdctl-wrapper-3.template @@ -0,0 +1,46 @@ +#!/bin/sh + +[ -f /etc/conf.d/ejabberd ] && . /etc/conf.d/ejabberd + +if [ -r /var/run/jabber/.erlang.cookie ] ; then + HOME=/var/run/jabber + export HOME +fi + +ERL=/usr/bin/erl + +if [ $# -ne 0 ] ; then + case $1 in + --node) shift ; EJABBERD_NODE=$1 ; shift ;; + esac +fi + +if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%.*}" ] ; then + SNAME=-sname +else + SNAME=-name +fi + +case $1 in + debug) + shift + + if [ "$EJABBERD_NODE" = "${EJABBERD_NODE%@*}" ] ; then + EJABBERD_NODE=$EJABBERD_NODE@$(hostname -s) + fi + + echo "Attaching Erlang shell to node $EJABBERD_NODE." + echo "To detach it, press: Ctrl+G, q, Return" + echo "" + exec $ERL $SNAME ejabberddebug \ + -remsh $EJABBERD_NODE \ + "$@" + ;; + *) +exec $ERL $SNAME ejabberdctl \ + -pa /usr/@libdir@/erlang/lib/ejabberd-@version@/ebin \ + -s ejabberd_ctl \ + -noinput \ + -extra $EJABBERD_NODE "$@" + ;; +esac diff --git a/net-im/ejabberd/files/inetrc b/net-im/ejabberd/files/inetrc new file mode 100644 index 0000000..2d2f635 --- /dev/null +++ b/net-im/ejabberd/files/inetrc @@ -0,0 +1 @@ +{file, resolv, "/etc/resolv.conf"}. diff --git a/net-im/ejabberd/files/self-cert-v2.sh b/net-im/ejabberd/files/self-cert-v2.sh new file mode 100644 index 0000000..b2f3b7d --- /dev/null +++ b/net-im/ejabberd/files/self-cert-v2.sh @@ -0,0 +1,41 @@ +#! /bin/sh +# +# self-cert.sh for ejabberd, stolen from: +# mkimapdcert,v 1.1 2001/01/02 03:54:25 drobbins Exp +# +# Copyright 2000 Double Precision, Inc. See COPYING for +# distribution information. +# +# This is a short script to quickly generate a self-signed X.509 key for +# eJabberd. Normally this script would get called by an automatic +# package installation routine. + +test -x /usr/bin/openssl || exit 0 + +prefix="/usr" +pemfile="/etc/jabber/ssl.pem" +randfile="/etc/jabber/ssl.rand" + +if test -f $pemfile +then + echo "$pemfile already exists." + exit 1 +fi + +cp /dev/null $pemfile +chmod 640 $pemfile +chown root:jabber $pemfile + +cleanup() { + rm -f $pemfile + rm -f $randfile + exit 1 +} + +dd if=/dev/urandom of=$randfile count=1 2>/dev/null +/usr/bin/openssl req -new -x509 -days 365 -nodes \ + -config /etc/jabber/ssl.cnf -out $pemfile -keyout $pemfile || cleanup +/usr/bin/openssl gendh -rand $randfile 512 >> $pemfile || cleanup +/usr/bin/openssl x509 -subject -dates -fingerprint -noout -in $pemfile || cleanup +rm -f $randfile + diff --git a/net-im/ejabberd/files/self-cert-v3.sh b/net-im/ejabberd/files/self-cert-v3.sh new file mode 100644 index 0000000..729c878 --- /dev/null +++ b/net-im/ejabberd/files/self-cert-v3.sh @@ -0,0 +1,128 @@ +#! /bin/sh +# Copyright 1999-2009 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Header: $ +# self-cert.sh for ejabberd + +openssl=$(which openssl) + +[[ -z "${openssl}" ]] && openssl="/usr/bin/openssl" + +if ! [[ -x "${openssl}" ]]; then + echo "openssl required for certificates" >&2 + exit 1 +fi + +usage() { + local error="$@" + + [[ -z "${error}" ]] || echo -e "Error: ${error}\n" + + cat <<USAGE | expand -t 8 +Usage: $0 [options] + +Options: + -h --help - this message + + -c --config=CONFIG - use specified openssl config + -o --output=PEMFILE - put generated key+cert into PEMFILE + [default: @SSL_CERT@] + + -f --force - force overwrite if output already exists + + -r --rand-file=FILE - use specified random file + --rand-source=DEV - use DEV as source, if generating + random file [defalt: /dev/urandom] +USAGE + + [[ -z "${error}" ]] && exit 0 + + exit 1 +} + +main() { + local config= output= rnd= rnd_source= force=false + + eval set -- x $(getopt -o c:r:o:hf -l config: -l help -l output: \ + -l force -l rand-file: -l rand-source: -- "$@") + shift; + + while [[ $# -gt 0 ]]; do + local arg=$1 + + case "${arg}" in + --help|-h) usage;; + --force|-f) force=true;; + --config|-c) config=$2; shift;; + --output|-o) output=$2; shift;; + --rand-file|-r) rnd=$2; shift;; + --rand-source) rnd_source=$2; shift;; + --) :;; + *) usage "Bad argument: ${arg}";; + esac + + shift; + done + + [[ -z "${config}" ]] && config="@SSL_CONFIG@" + [[ -z "${output}" ]] && output="@SSL_CERT@" + [[ -z "${rnd}" ]] && rnd=$(mktemp) + + if [[ -z "${rnd_source}" ]]; then + [[ -r /dev/urandom ]] && rnd_source=/dev/urandom + + rnd_source=/dev/random + fi + + [[ -r "${config}" ]] || \ + usage "Config '${config}' not readable" + + [[ -w "${output}" || -w "$(dirname "${output}")" ]] || \ + usage "Output '${output}' not writable" + + [[ -r "${rnd_source}" ]] || \ + usage "rand-source '${rnd_source}' not readble" + + if [[ -f "${output}" ]]; then + ${force} || \ + usage "Output file '${output}' already exists." + fi + + cp /dev/null "${output}" + + chmod 640 "${output}" + chown root:jabber "${output}" + + cleanup() { + local message=$1 + + rm -f "${output}" "${rnd}" + + echo "Error: ${message}" + exit 2 + } + + if ! [[ -r "${rnd}" ]]; then + [[ -w ${rnd} ]] && \ + usage "No write permission for rand-file: '${rnd}'" + + dd if="${rnd_source}" of="${rnd}" count=1 2>/dev/null + fi + + "${openssl}" req -new -x509 -days 365 -nodes -config "${config}" \ + -out "${output}" -keyout "${output}" || \ + cleanup "Creating key failed" + + "${openssl}" gendh -rand "${rnd}" 512 >> "${output}" || \ + cleanup "Adding of required extensions failed" + + "${openssl}" x509 -subject -dates -fingerprint \ + -noout -in "${output}" || \ + cleanup "Certificating failed" + + rm -f "${rnd}" + + exit 0 +} + +main "$@" diff --git a/net-im/ejabberd/files/self-cert.sh b/net-im/ejabberd/files/self-cert.sh new file mode 100644 index 0000000..2c984fd --- /dev/null +++ b/net-im/ejabberd/files/self-cert.sh @@ -0,0 +1,21 @@ +#!/bin/bash + +###### +# +# Generate a certificate and key with no passphrase. +# +###### + +OPENSSL=/usr/bin/openssl + +## This generates the cert and key +$OPENSSL req -new -x509 -newkey rsa:1024 -keyout /tmp/privkey.pem -out /etc/ejabberd/ssl.pem +## This will remove the passphrase +$OPENSSL rsa -in /tmp/privkey.pem -out /tmp/privkey.pem +## Put it all together +cat /tmp/privkey.pem >> /etc/ejabberd/ssl.pem +## Cleanup +rm /tmp/privkey.pem +echo "" +echo "Your new key is /etc/ejabberd/ssl.pem" +echo "" diff --git a/net-im/ejabberd/files/ssl.cnf b/net-im/ejabberd/files/ssl.cnf new file mode 100644 index 0000000..7a51d91 --- /dev/null +++ b/net-im/ejabberd/files/ssl.cnf @@ -0,0 +1,36 @@ +# $Header: /var/cvsroot/gentoo-x86/net-im/ejabberd/files/ssl.cnf,v 1.1 2006/10/12 16:26:07 chainsaw Exp $ +# This is the openssl config file to generate keys for ejabberd +# It is read by self-cert.sh + +[ req ] +# you can increase this value, but be aware that it will make things much slower +# this should be a power of 2! +default_bits = 1024 +# leave the rest of these alone! +encrypt_key = yes +distinguished_name = req_dn +x509_extensions = cert_type +prompt = no + +[ req_dn ] +# 2-Letter ISO country code +C=UK +# FULL name of state/province/district +# NO abbreviations! +ST=Cambridgeshire +# FULL name of city +# NO abbreviations! +L=Peterborough +# Full Name of your organization +# NO abbreviations! +O=Bits and Bobs Ltd. +# Leave this alone unless specifically need to change it! +OU=Automatically-generated ejabberd SSL key +# This should be a FQDN that resolves to the IP of your server +CN=localhost +# This should be the email address for the administrator of the server +emailAddress=root@localhost + +# Leave this alone! +[ cert_type ] +nsCertType = server diff --git a/net-im/ejabberd/metadata.xml b/net-im/ejabberd/metadata.xml new file mode 100644 index 0000000..c694dee --- /dev/null +++ b/net-im/ejabberd/metadata.xml @@ -0,0 +1,20 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!DOCTYPE pkgmetadata SYSTEM "http://www.gentoo.org/dtd/metadata.dtd"> + +<pkgmetadata> +<herd>net-im</herd> +<maintainer> + <email>caleb@gentoo.org</email> +</maintainer> +<longdescription> Free and Open Source distributed fault-tolerant Jabber server. It's mostly written in Erlang, and works on many platforms.</longdescription> + <use> + <flag name='mod_irc'>Build irc gateway </flag> + <flag name='mod_muc'>Build Multi User Chat module</flag> + <flag name='mod_pubsub'>Build Pubsub module</flag> + <flag name='web'>Enable web admin interface</flag> + <flag name="captcha">Support for CAPTCHA Forms (XEP-158)</flag> + <flag name="mod_proxy65">Support for SOCKS5 Bytestreams (XEP-0065)</flag> + <flag name="mod_ctlextra">Additional Commands for ejabberdctl</flag> + <flag name="mod_statsdx">Measures several statistics, and provides a new section in ejabberd Web Admin to view them.</flag> + </use> +</pkgmetadata> |