mirror of
https://github.com/processone/ejabberd.git
synced 2024-06-14 22:00:16 +02:00
* src/odbc/odbc_queries.erl: Support for Microsoft SQL Server as
a database backend (via ODBC). * src/odbc/ejabberd_odbc.erl: Likewise. * src/odbc/mssql.sql: Likewise. * src/odbc/Makefile.in: Likewise. * src/ejabberd_auth_odbc.erl: Likewise. * src/mod_offline_odbc.erl: Likewise. * src/mod_roster_odbc.erl: Likewise. * src/mod_last_odbc.erl: Likewise. * src/configure.ac: Likewise * doc/guide.tex: Likewise. * doc/introduction.tex: Likewise. * src/odbc/pg.sql: Minor fix. SVN Revision: 598
This commit is contained in:
parent
40c8c8b559
commit
d0e2ac9ed2
16
ChangeLog
16
ChangeLog
|
@ -1,3 +1,19 @@
|
||||||
|
2006-09-03 Mickael Remond <mickael.remond@process-one.net>
|
||||||
|
|
||||||
|
* src/odbc/odbc_queries.erl: Support for Microsoft SQL Server as a
|
||||||
|
database backend (via ODBC).
|
||||||
|
* src/odbc/ejabberd_odbc.erl: Likewise.
|
||||||
|
* src/odbc/mssql.sql: Likewise.
|
||||||
|
* src/odbc/Makefile.in: Likewise.
|
||||||
|
* src/ejabberd_auth_odbc.erl: Likewise.
|
||||||
|
* src/mod_offline_odbc.erl: Likewise.
|
||||||
|
* src/mod_roster_odbc.erl: Likewise.
|
||||||
|
* src/mod_last_odbc.erl: Likewise.
|
||||||
|
* src/configure.ac: Likewise
|
||||||
|
* doc/guide.tex: Likewise.
|
||||||
|
* doc/introduction.tex: Likewise.
|
||||||
|
* src/odbc/pg.sql: Minor fix.
|
||||||
|
|
||||||
2006-08-28 Mickael Remond <mickael.remond@process-one.net>
|
2006-08-28 Mickael Remond <mickael.remond@process-one.net>
|
||||||
|
|
||||||
* Makefile.in: Fix for MacOSX compilation.
|
* Makefile.in: Fix for MacOSX compilation.
|
||||||
|
|
|
@ -153,6 +153,7 @@ Native MySQL support.
|
||||||
<LI CLASS="li-itemize">Native PostgreSQL support.
|
<LI CLASS="li-itemize">Native PostgreSQL support.
|
||||||
<LI CLASS="li-itemize">Mnesia.
|
<LI CLASS="li-itemize">Mnesia.
|
||||||
<LI CLASS="li-itemize">ODBC data storage support.
|
<LI CLASS="li-itemize">ODBC data storage support.
|
||||||
|
<LI CLASS="li-itemize">Microsoft SQL Server support (via ODBC).
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-itemize">Authentication
|
<LI CLASS="li-itemize">Authentication
|
||||||
<UL CLASS="itemize"><LI CLASS="li-itemize">
|
<UL CLASS="itemize"><LI CLASS="li-itemize">
|
||||||
|
|
214
doc/guide.html
214
doc/guide.html
|
@ -92,68 +92,69 @@ BLOCKQUOTE{margin-left:4ex;margin-right:4ex;text-align:left;}
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc24">3.2 Relational Database Support</A>
|
<LI CLASS="li-toc"><A HREF="#htoc24">3.2 Relational Database Support</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc25">3.2.1 Authentication against a relational database</A>
|
<A HREF="#htoc25">3.2.1 Preliminary steps</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc26">3.2.2 Relational database for other modules</A>
|
<LI CLASS="li-toc"><A HREF="#htoc26">3.2.2 Authentication against a relational database</A>
|
||||||
|
<LI CLASS="li-toc"><A HREF="#htoc27">3.2.3 Relational database for other modules</A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc27">3.3 Creating an Initial Administrator</A>
|
<LI CLASS="li-toc"><A HREF="#htoc28">3.3 Creating an Initial Administrator</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc28">3.4 Online Configuration and Monitoring</A>
|
<LI CLASS="li-toc"><A HREF="#htoc29">3.4 Online Configuration and Monitoring</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc29">3.4.1 Web Interface</A>
|
<A HREF="#htoc30">3.4.1 Web Interface</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc30">3.4.2 <TT>ejabberdctl</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc31">3.4.2 <TT>ejabberdctl</TT></A>
|
||||||
</UL>
|
</UL>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc31">4 Firewall Settings</A>
|
<LI CLASS="li-toc"><A HREF="#htoc32">4 Firewall Settings</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc32">5 SRV Records</A>
|
<LI CLASS="li-toc"><A HREF="#htoc33">5 SRV Records</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc33">6 Clustering</A>
|
<LI CLASS="li-toc"><A HREF="#htoc34">6 Clustering</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc34">6.1 How it Works</A>
|
<A HREF="#htoc35">6.1 How it Works</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc35">6.1.1 Router</A>
|
<A HREF="#htoc36">6.1.1 Router</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc36">6.1.2 Local Router</A>
|
<LI CLASS="li-toc"><A HREF="#htoc37">6.1.2 Local Router</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc37">6.1.3 Session Manager</A>
|
<LI CLASS="li-toc"><A HREF="#htoc38">6.1.3 Session Manager</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc38">6.1.4 s2s Manager</A>
|
<LI CLASS="li-toc"><A HREF="#htoc39">6.1.4 s2s Manager</A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc39">6.2 Clustering Setup</A>
|
<LI CLASS="li-toc"><A HREF="#htoc40">6.2 Clustering Setup</A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc40">A Built-in Modules</A>
|
<LI CLASS="li-toc"><A HREF="#htoc41">A Built-in Modules</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc41">A.1 Overview</A>
|
<A HREF="#htoc42">A.1 Overview</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc42">A.2 Common Options</A>
|
<LI CLASS="li-toc"><A HREF="#htoc43">A.2 Common Options</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc43">A.2.1 <TT>iqdisc</TT></A>
|
<A HREF="#htoc44">A.2.1 <TT>iqdisc</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc44">A.2.2 <TT>hosts</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc45">A.2.2 <TT>hosts</TT></A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc45">A.3 <TT>mod_announce</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc46">A.3 <TT>mod_announce</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc46">A.4 <TT>mod_disco</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc47">A.4 <TT>mod_disco</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc47">A.5 <TT>mod_echo</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc48">A.5 <TT>mod_echo</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc48">A.6 <TT>mod_irc</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc49">A.6 <TT>mod_irc</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc49">A.7 <TT>mod_last</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc50">A.7 <TT>mod_last</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc50">A.8 <TT>mod_muc</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc51">A.8 <TT>mod_muc</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc51">A.9 <TT>mod_muc_log</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc52">A.9 <TT>mod_muc_log</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc52">A.10 <TT>mod_offline</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc53">A.10 <TT>mod_offline</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc53">A.11 <TT>mod_privacy</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc54">A.11 <TT>mod_privacy</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc54">A.12 <TT>mod_private</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc55">A.12 <TT>mod_private</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc55">A.13 <TT>mod_pubsub</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc56">A.13 <TT>mod_pubsub</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc56">A.14 <TT>mod_register</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc57">A.14 <TT>mod_register</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc57">A.15 <TT>mod_roster</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc58">A.15 <TT>mod_roster</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc58">A.16 <TT>mod_service_log</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc59">A.16 <TT>mod_service_log</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc59">A.17 <TT>mod_shared_roster</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc60">A.17 <TT>mod_shared_roster</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc60">A.18 <TT>mod_stats</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc61">A.18 <TT>mod_stats</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc61">A.19 <TT>mod_time</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc62">A.19 <TT>mod_time</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc62">A.20 <TT>mod_vcard</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc63">A.20 <TT>mod_vcard</TT></A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc63">A.21 <TT>mod_version</TT></A>
|
<LI CLASS="li-toc"><A HREF="#htoc64">A.21 <TT>mod_version</TT></A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc64">B Internationalization and Localization</A>
|
<LI CLASS="li-toc"><A HREF="#htoc65">B Internationalization and Localization</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc65">C Release Notes</A>
|
<LI CLASS="li-toc"><A HREF="#htoc66">C Release Notes</A>
|
||||||
<UL CLASS="toc"><LI CLASS="li-toc">
|
<UL CLASS="toc"><LI CLASS="li-toc">
|
||||||
<A HREF="#htoc66">C.1 ejabberd 0.9</A>
|
<A HREF="#htoc67">C.1 ejabberd 0.9</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc67">C.2 ejabberd 0.9.1</A>
|
<LI CLASS="li-toc"><A HREF="#htoc68">C.2 ejabberd 0.9.1</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc68">C.3 ejabberd 0.9.8</A>
|
<LI CLASS="li-toc"><A HREF="#htoc69">C.3 ejabberd 0.9.8</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc69">C.4 ejabberd 1.0.0</A>
|
<LI CLASS="li-toc"><A HREF="#htoc70">C.4 ejabberd 1.0.0</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc70">C.5 ejabberd 1.1.0</A>
|
<LI CLASS="li-toc"><A HREF="#htoc71">C.5 ejabberd 1.1.0</A>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc71">C.6 ejabberd 1.1.1</A>
|
<LI CLASS="li-toc"><A HREF="#htoc72">C.6 ejabberd 1.1.1</A>
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-toc"><A HREF="#htoc72">D Acknowledgements</A>
|
<LI CLASS="li-toc"><A HREF="#htoc73">D Acknowledgements</A>
|
||||||
</UL>
|
</UL>
|
||||||
|
|
||||||
<!--TOC section Introduction-->
|
<!--TOC section Introduction-->
|
||||||
|
@ -230,6 +231,7 @@ Native MySQL support.
|
||||||
<LI CLASS="li-itemize">Native PostgreSQL support.
|
<LI CLASS="li-itemize">Native PostgreSQL support.
|
||||||
<LI CLASS="li-itemize">Mnesia.
|
<LI CLASS="li-itemize">Mnesia.
|
||||||
<LI CLASS="li-itemize">ODBC data storage support.
|
<LI CLASS="li-itemize">ODBC data storage support.
|
||||||
|
<LI CLASS="li-itemize">Microsoft SQL Server support (via ODBC).
|
||||||
</UL>
|
</UL>
|
||||||
<LI CLASS="li-itemize">Authentication
|
<LI CLASS="li-itemize">Authentication
|
||||||
<UL CLASS="itemize"><LI CLASS="li-itemize">
|
<UL CLASS="itemize"><LI CLASS="li-itemize">
|
||||||
|
@ -973,9 +975,29 @@ available from:
|
||||||
<H3 CLASS="subsection"><A NAME="htoc24">3.2</A> Relational Database Support</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc24">3.2</A> Relational Database Support</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:relationaldatabase"></A>
|
<A NAME="sec:relationaldatabase"></A>
|
||||||
|
<!--TOC subsubsection Preliminary steps-->
|
||||||
|
|
||||||
|
<H4 CLASS="subsubsection"><A NAME="htoc25">3.2.1</A> Preliminary steps</H4><!--SEC END -->
|
||||||
|
|
||||||
|
<A NAME="sec:relationaldatabasecompilation"></A>
|
||||||
|
If you have installed ejabberd using a binary version, the compilation steps
|
||||||
|
are not needed as they have already been done correctly.<BR>
|
||||||
|
<BR>
|
||||||
|
Otherwise, to be able to use ejabberd with a relational database you need to
|
||||||
|
enable ODBC modules during compilation, even if you want to use ejabberd with
|
||||||
|
MySQL or PostgreSQL in native mode. The following <TT>configure</TT> command can
|
||||||
|
be used to enable the relational modules:
|
||||||
|
<PRE CLASS="verbatim">
|
||||||
|
./configure --enable-odbc
|
||||||
|
</PRE>
|
||||||
|
If you are planning to use Microsoft SQL Server with ODBC, you need to specify
|
||||||
|
it from the <TT>configure</TT> command before compilation:
|
||||||
|
<PRE CLASS="verbatim">
|
||||||
|
./configure --enable-odbc --enable-mssql
|
||||||
|
</PRE>
|
||||||
<!--TOC subsubsection Authentication against a relational database-->
|
<!--TOC subsubsection Authentication against a relational database-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc25">3.2.1</A> Authentication against a relational database</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc26">3.2.2</A> Authentication against a relational database</H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:relationaldatabaseauth"></A>
|
<A NAME="sec:relationaldatabaseauth"></A>
|
||||||
ejabberd use its internal Mnesia database as a default. It is however possible
|
ejabberd use its internal Mnesia database as a default. It is however possible
|
||||||
|
@ -1030,7 +1052,7 @@ available from: <A HREF="http://support.process-one.net/doc/display/MESSENGER/Us
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsubsection Relational database for other modules-->
|
<!--TOC subsubsection Relational database for other modules-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc26">3.2.2</A> Relational database for other modules</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc27">3.2.3</A> Relational database for other modules</H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:relationaldatabaseextra"></A>
|
<A NAME="sec:relationaldatabaseextra"></A>
|
||||||
It is possible to use a relational database to store pieces of
|
It is possible to use a relational database to store pieces of
|
||||||
|
@ -1047,7 +1069,7 @@ Last connection date and time: Use <TT>mod_last_odbc</TT> instead of
|
||||||
</UL>
|
</UL>
|
||||||
<!--TOC subsection Creating an Initial Administrator-->
|
<!--TOC subsection Creating an Initial Administrator-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc27">3.3</A> Creating an Initial Administrator</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc28">3.3</A> Creating an Initial Administrator</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:initialadmin"></A>
|
<A NAME="sec:initialadmin"></A>
|
||||||
Before the web interface can be entered to perform administration tasks, an
|
Before the web interface can be entered to perform administration tasks, an
|
||||||
|
@ -1079,12 +1101,12 @@ Register an account on your <TT>ejabberd</TT> deployment. An account can be
|
||||||
</OL>
|
</OL>
|
||||||
<!--TOC subsection Online Configuration and Monitoring-->
|
<!--TOC subsection Online Configuration and Monitoring-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc28">3.4</A> Online Configuration and Monitoring</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc29">3.4</A> Online Configuration and Monitoring</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:onlineconfig"></A>
|
<A NAME="sec:onlineconfig"></A>
|
||||||
<!--TOC subsubsection Web Interface-->
|
<!--TOC subsubsection Web Interface-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc29">3.4.1</A> Web Interface</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc30">3.4.1</A> Web Interface</H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:webadm"></A>
|
<A NAME="sec:webadm"></A>
|
||||||
|
|
||||||
|
@ -1158,7 +1180,7 @@ You can serve the web interface on the same port as the
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsubsection <TT>ejabberdctl</TT>-->
|
<!--TOC subsubsection <TT>ejabberdctl</TT>-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc30">3.4.2</A> <TT>ejabberdctl</TT></H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc31">3.4.2</A> <TT>ejabberdctl</TT></H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:ejabberdctl"></A>
|
<A NAME="sec:ejabberdctl"></A>
|
||||||
It is possible to do some administration operations using the command
|
It is possible to do some administration operations using the command
|
||||||
|
@ -1204,7 +1226,7 @@ Additional information:
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC section Firewall Settings-->
|
<!--TOC section Firewall Settings-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc31">4</A> Firewall Settings</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc32">4</A> Firewall Settings</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:firewall"></A>
|
<A NAME="sec:firewall"></A>
|
||||||
|
|
||||||
|
@ -1233,7 +1255,7 @@ You need to take the following TCP ports in mind when configuring your firewall:
|
||||||
<DIV CLASS="center"><HR WIDTH="80%" SIZE=2></DIV></DIV></BLOCKQUOTE>
|
<DIV CLASS="center"><HR WIDTH="80%" SIZE=2></DIV></DIV></BLOCKQUOTE>
|
||||||
<!--TOC section SRV Records-->
|
<!--TOC section SRV Records-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc32">5</A> SRV Records</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc33">5</A> SRV Records</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:srv"></A>
|
<A NAME="sec:srv"></A>
|
||||||
|
|
||||||
|
@ -1245,13 +1267,13 @@ General information:
|
||||||
</UL>
|
</UL>
|
||||||
<!--TOC section Clustering-->
|
<!--TOC section Clustering-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc33">6</A> Clustering</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc34">6</A> Clustering</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:clustering"></A>
|
<A NAME="sec:clustering"></A>
|
||||||
|
|
||||||
<!--TOC subsection How it Works-->
|
<!--TOC subsection How it Works-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc34">6.1</A> How it Works</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc35">6.1</A> How it Works</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:howitworks"></A>
|
<A NAME="sec:howitworks"></A>
|
||||||
|
|
||||||
|
@ -1272,7 +1294,7 @@ router,
|
||||||
</UL>
|
</UL>
|
||||||
<!--TOC subsubsection Router-->
|
<!--TOC subsubsection Router-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc35">6.1.1</A> Router</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc36">6.1.1</A> Router</H4><!--SEC END -->
|
||||||
|
|
||||||
|
|
||||||
This module is the main router of Jabber packets on each node. It
|
This module is the main router of Jabber packets on each node. It
|
||||||
|
@ -1283,7 +1305,7 @@ appropriate process. If not, it is sent to the s2s manager.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsubsection Local Router-->
|
<!--TOC subsubsection Local Router-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc36">6.1.2</A> Local Router</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc37">6.1.2</A> Local Router</H4><!--SEC END -->
|
||||||
|
|
||||||
|
|
||||||
This module routes packets which have a destination domain equal to
|
This module routes packets which have a destination domain equal to
|
||||||
|
@ -1293,7 +1315,7 @@ on its content.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsubsection Session Manager-->
|
<!--TOC subsubsection Session Manager-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc37">6.1.3</A> Session Manager</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc38">6.1.3</A> Session Manager</H4><!--SEC END -->
|
||||||
|
|
||||||
|
|
||||||
This module routes packets to local users. It looks up to which user
|
This module routes packets to local users. It looks up to which user
|
||||||
|
@ -1303,7 +1325,7 @@ storage, or bounced back.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsubsection s2s Manager-->
|
<!--TOC subsubsection s2s Manager-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc38">6.1.4</A> s2s Manager</H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc39">6.1.4</A> s2s Manager</H4><!--SEC END -->
|
||||||
|
|
||||||
|
|
||||||
This module routes packets to other Jabber servers. First, it
|
This module routes packets to other Jabber servers. First, it
|
||||||
|
@ -1314,7 +1336,7 @@ serving this connection, otherwise a new connection is opened.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsection Clustering Setup-->
|
<!--TOC subsection Clustering Setup-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc39">6.2</A> Clustering Setup</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc40">6.2</A> Clustering Setup</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:cluster"></A>
|
<A NAME="sec:cluster"></A>
|
||||||
|
|
||||||
|
@ -1387,13 +1409,13 @@ domain.<BR>
|
||||||
|
|
||||||
<!--TOC section Built-in Modules-->
|
<!--TOC section Built-in Modules-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc40">A</A> Built-in Modules</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc41">A</A> Built-in Modules</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modules"></A>
|
<A NAME="sec:modules"></A>
|
||||||
|
|
||||||
<!--TOC subsection Overview-->
|
<!--TOC subsection Overview-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc41">A.1</A> Overview</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc42">A.1</A> Overview</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modoverview"></A>
|
<A NAME="sec:modoverview"></A>
|
||||||
|
|
||||||
|
@ -1605,7 +1627,7 @@ XMPP compliancy.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsection Common Options-->
|
<!--TOC subsection Common Options-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc42">A.2</A> Common Options</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc43">A.2</A> Common Options</H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modcommonopts"></A>
|
<A NAME="sec:modcommonopts"></A>
|
||||||
The following options are used by many modules. Therefore, they are described in
|
The following options are used by many modules. Therefore, they are described in
|
||||||
|
@ -1613,7 +1635,7 @@ this separate section.<BR>
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsubsection <TT>iqdisc</TT>-->
|
<!--TOC subsubsection <TT>iqdisc</TT>-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc43">A.2.1</A> <TT>iqdisc</TT></H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc44">A.2.1</A> <TT>iqdisc</TT></H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modiqdiscoption"></A>
|
<A NAME="sec:modiqdiscoption"></A>
|
||||||
|
|
||||||
|
@ -1647,7 +1669,7 @@ Example:
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsubsection <TT>hosts</TT>-->
|
<!--TOC subsubsection <TT>hosts</TT>-->
|
||||||
|
|
||||||
<H4 CLASS="subsubsection"><A NAME="htoc44">A.2.2</A> <TT>hosts</TT></H4><!--SEC END -->
|
<H4 CLASS="subsubsection"><A NAME="htoc45">A.2.2</A> <TT>hosts</TT></H4><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modhostsoption"></A>
|
<A NAME="sec:modhostsoption"></A>
|
||||||
|
|
||||||
|
@ -1686,7 +1708,7 @@ Serving the echo module on one domain:
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_announce</TT>-->
|
<!--TOC subsection <TT>mod_announce</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc45">A.3</A> <TT>mod_announce</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc46">A.3</A> <TT>mod_announce</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modannounce"></A>
|
<A NAME="sec:modannounce"></A>
|
||||||
|
|
||||||
|
@ -1752,7 +1774,7 @@ Only administrators can send announcements:
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_disco</TT>-->
|
<!--TOC subsection <TT>mod_disco</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc46">A.4</A> <TT>mod_disco</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc47">A.4</A> <TT>mod_disco</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:moddisco"></A>
|
<A NAME="sec:moddisco"></A>
|
||||||
|
|
||||||
|
@ -1804,7 +1826,7 @@ To serve a link to the Jabber User Directory on <TT>jabber.org</TT>:
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_echo</TT>-->
|
<!--TOC subsection <TT>mod_echo</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc47">A.5</A> <TT>mod_echo</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc48">A.5</A> <TT>mod_echo</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modecho"></A>
|
<A NAME="sec:modecho"></A>
|
||||||
|
|
||||||
|
@ -1837,7 +1859,7 @@ Mirror, mirror, on the wall, who is the most beautiful
|
||||||
</UL>
|
</UL>
|
||||||
<!--TOC subsection <TT>mod_irc</TT>-->
|
<!--TOC subsection <TT>mod_irc</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc48">A.6</A> <TT>mod_irc</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc49">A.6</A> <TT>mod_irc</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modirc"></A>
|
<A NAME="sec:modirc"></A>
|
||||||
|
|
||||||
|
@ -1907,7 +1929,7 @@ In the first example, the IRC transport is available on (all) your
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_last</TT>-->
|
<!--TOC subsection <TT>mod_last</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc49">A.7</A> <TT>mod_last</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc50">A.7</A> <TT>mod_last</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modlast"></A>
|
<A NAME="sec:modlast"></A>
|
||||||
|
|
||||||
|
@ -1924,7 +1946,7 @@ the processing discipline for Last activity (<TT>jabber:iq:last</TT>) IQ queries
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC subsection <TT>mod_muc</TT>-->
|
<!--TOC subsection <TT>mod_muc</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc50">A.8</A> <TT>mod_muc</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc51">A.8</A> <TT>mod_muc</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modmuc"></A>
|
<A NAME="sec:modmuc"></A>
|
||||||
|
|
||||||
|
@ -2014,7 +2036,7 @@ In the first example everyone is allowed to use the Multi-User Chat
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_muc_log</TT>-->
|
<!--TOC subsection <TT>mod_muc_log</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc51">A.9</A> <TT>mod_muc_log</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc52">A.9</A> <TT>mod_muc_log</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modmuclog"></A>
|
<A NAME="sec:modmuclog"></A>
|
||||||
|
|
||||||
|
@ -2086,7 +2108,7 @@ Example configuration:
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection <TT>mod_offline</TT>-->
|
<!--TOC subsection <TT>mod_offline</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc52">A.10</A> <TT>mod_offline</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc53">A.10</A> <TT>mod_offline</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modoffline"></A>
|
<A NAME="sec:modoffline"></A>
|
||||||
|
|
||||||
|
@ -2098,7 +2120,7 @@ online again. Thus it is very similar to how email works. Note that
|
||||||
<BR>
|
<BR>
|
||||||
<!--TOC subsection <TT>mod_privacy</TT>-->
|
<!--TOC subsection <TT>mod_privacy</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc53">A.11</A> <TT>mod_privacy</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc54">A.11</A> <TT>mod_privacy</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modprivacy"></A>
|
<A NAME="sec:modprivacy"></A>
|
||||||
|
|
||||||
|
@ -2133,7 +2155,7 @@ the processing discipline for Blocking Communication (<TT>jabber:iq:privacy</TT>
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC subsection <TT>mod_private</TT>-->
|
<!--TOC subsection <TT>mod_private</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc54">A.12</A> <TT>mod_private</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc55">A.12</A> <TT>mod_private</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modprivate"></A>
|
<A NAME="sec:modprivate"></A>
|
||||||
|
|
||||||
|
@ -2152,7 +2174,7 @@ the processing discipline for Private XML Storage (<TT>jabber:iq:private</TT>) I
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC subsection <TT>mod_pubsub</TT>-->
|
<!--TOC subsection <TT>mod_pubsub</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc55">A.13</A> <TT>mod_pubsub</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc56">A.13</A> <TT>mod_pubsub</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modpubsub"></A>
|
<A NAME="sec:modpubsub"></A>
|
||||||
|
|
||||||
|
@ -2205,7 +2227,7 @@ Example:
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection <TT>mod_register</TT>-->
|
<!--TOC subsection <TT>mod_register</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc56">A.14</A> <TT>mod_register</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc57">A.14</A> <TT>mod_register</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modregister"></A>
|
<A NAME="sec:modregister"></A>
|
||||||
|
|
||||||
|
@ -2262,7 +2284,7 @@ Next example prohibits the registration of too short account names and of
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_roster</TT>-->
|
<!--TOC subsection <TT>mod_roster</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc57">A.15</A> <TT>mod_roster</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc58">A.15</A> <TT>mod_roster</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modroster"></A>
|
<A NAME="sec:modroster"></A>
|
||||||
|
|
||||||
|
@ -2276,7 +2298,7 @@ the processing discipline for Roster Management (<TT>jabber:iq:roster</TT>) IQ q
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC subsection <TT>mod_service_log</TT>-->
|
<!--TOC subsection <TT>mod_service_log</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc58">A.16</A> <TT>mod_service_log</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc59">A.16</A> <TT>mod_service_log</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modservicelog"></A>
|
<A NAME="sec:modservicelog"></A>
|
||||||
|
|
||||||
|
@ -2316,7 +2338,7 @@ To log all end user packets to the Bandersnatch service running on
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_shared_roster</TT>-->
|
<!--TOC subsection <TT>mod_shared_roster</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc59">A.17</A> <TT>mod_shared_roster</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc60">A.17</A> <TT>mod_shared_roster</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modsharedroster"></A>
|
<A NAME="sec:modsharedroster"></A>
|
||||||
|
|
||||||
|
@ -2443,7 +2465,7 @@ Take the case of a computer club that wants all its members seeing each
|
||||||
</UL>
|
</UL>
|
||||||
<!--TOC subsection <TT>mod_stats</TT>-->
|
<!--TOC subsection <TT>mod_stats</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc60">A.18</A> <TT>mod_stats</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc61">A.18</A> <TT>mod_stats</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modstats"></A>
|
<A NAME="sec:modstats"></A>
|
||||||
|
|
||||||
|
@ -2485,7 +2507,7 @@ You can request the number of online users on the current virtual host
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_time</TT>-->
|
<!--TOC subsection <TT>mod_time</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc61">A.19</A> <TT>mod_time</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc62">A.19</A> <TT>mod_time</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modtime"></A>
|
<A NAME="sec:modtime"></A>
|
||||||
|
|
||||||
|
@ -2500,7 +2522,7 @@ the processing discipline for Entity Time (<TT>jabber:iq:time</TT>) IQ queries
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC subsection <TT>mod_vcard</TT>-->
|
<!--TOC subsection <TT>mod_vcard</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc62">A.20</A> <TT>mod_vcard</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc63">A.20</A> <TT>mod_vcard</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modvcard"></A>
|
<A NAME="sec:modvcard"></A>
|
||||||
|
|
||||||
|
@ -2566,7 +2588,7 @@ In this first situation, search results are limited to twenty items,
|
||||||
</PRE></UL>
|
</PRE></UL>
|
||||||
<!--TOC subsection <TT>mod_version</TT>-->
|
<!--TOC subsection <TT>mod_version</TT>-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc63">A.21</A> <TT>mod_version</TT></H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc64">A.21</A> <TT>mod_version</TT></H3><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:modversion"></A>
|
<A NAME="sec:modversion"></A>
|
||||||
|
|
||||||
|
@ -2581,7 +2603,7 @@ the processing discipline for Software Version (<TT>jabber:iq:version</TT>) IQ q
|
||||||
</DL>
|
</DL>
|
||||||
<!--TOC section Internationalization and Localization-->
|
<!--TOC section Internationalization and Localization-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc64">B</A> Internationalization and Localization</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc65">B</A> Internationalization and Localization</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:i18nl10n"></A>
|
<A NAME="sec:i18nl10n"></A>
|
||||||
|
|
||||||
|
@ -2624,13 +2646,13 @@ figure <A HREF="#fig:webadmmainru">3</A> with figure <A HREF="#fig:web
|
||||||
<DIV CLASS="center"><HR WIDTH="80%" SIZE=2></DIV></DIV></BLOCKQUOTE>
|
<DIV CLASS="center"><HR WIDTH="80%" SIZE=2></DIV></DIV></BLOCKQUOTE>
|
||||||
<!--TOC section Release Notes-->
|
<!--TOC section Release Notes-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc65">C</A> Release Notes</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc66">C</A> Release Notes</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:releasenotes"></A>
|
<A NAME="sec:releasenotes"></A>
|
||||||
|
|
||||||
<!--TOC subsection ejabberd 0.9-->
|
<!--TOC subsection ejabberd 0.9-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc66">C.1</A> ejabberd 0.9</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc67">C.1</A> ejabberd 0.9</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release notes
|
Release notes
|
||||||
|
@ -2724,7 +2746,7 @@ Bugfixes
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection ejabberd 0.9.1-->
|
<!--TOC subsection ejabberd 0.9.1-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc67">C.2</A> ejabberd 0.9.1</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc68">C.2</A> ejabberd 0.9.1</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release notes
|
Release notes
|
||||||
|
@ -2792,7 +2814,7 @@ Bugfixes
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection ejabberd 0.9.8-->
|
<!--TOC subsection ejabberd 0.9.8-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc68">C.3</A> ejabberd 0.9.8</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc69">C.3</A> ejabberd 0.9.8</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release notes
|
Release notes
|
||||||
|
@ -2897,7 +2919,7 @@ END
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection ejabberd 1.0.0-->
|
<!--TOC subsection ejabberd 1.0.0-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc69">C.4</A> ejabberd 1.0.0</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc70">C.4</A> ejabberd 1.0.0</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release Notes
|
Release Notes
|
||||||
|
@ -3023,7 +3045,7 @@ END
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection ejabberd 1.1.0-->
|
<!--TOC subsection ejabberd 1.1.0-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc70">C.5</A> ejabberd 1.1.0</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc71">C.5</A> ejabberd 1.1.0</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release Notes
|
Release Notes
|
||||||
|
@ -3144,7 +3166,7 @@ END
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC subsection ejabberd 1.1.1-->
|
<!--TOC subsection ejabberd 1.1.1-->
|
||||||
|
|
||||||
<H3 CLASS="subsection"><A NAME="htoc71">C.6</A> ejabberd 1.1.1</H3><!--SEC END -->
|
<H3 CLASS="subsection"><A NAME="htoc72">C.6</A> ejabberd 1.1.1</H3><!--SEC END -->
|
||||||
|
|
||||||
<PRE CLASS="verbatim">
|
<PRE CLASS="verbatim">
|
||||||
Release Notes
|
Release Notes
|
||||||
|
@ -3269,7 +3291,7 @@ END
|
||||||
</PRE>
|
</PRE>
|
||||||
<!--TOC section Acknowledgements-->
|
<!--TOC section Acknowledgements-->
|
||||||
|
|
||||||
<H2 CLASS="section"><A NAME="htoc72">D</A> Acknowledgements</H2><!--SEC END -->
|
<H2 CLASS="section"><A NAME="htoc73">D</A> Acknowledgements</H2><!--SEC END -->
|
||||||
|
|
||||||
<A NAME="sec:acknowledgements"></A>
|
<A NAME="sec:acknowledgements"></A>
|
||||||
|
|
||||||
|
|
|
@ -860,6 +860,26 @@ available from:
|
||||||
\subsection{Relational Database Support}
|
\subsection{Relational Database Support}
|
||||||
\label{sec:relationaldatabase}
|
\label{sec:relationaldatabase}
|
||||||
|
|
||||||
|
\subsubsection{Preliminary steps}
|
||||||
|
\label{sec:relationaldatabasecompilation}
|
||||||
|
|
||||||
|
If you have installed ejabberd using a binary version, the compilation steps
|
||||||
|
are not needed as they have already been done correctly.
|
||||||
|
|
||||||
|
Otherwise, to be able to use ejabberd with a relational database you need to
|
||||||
|
enable ODBC modules during compilation, even if you want to use ejabberd with
|
||||||
|
MySQL or PostgreSQL in native mode. The following \term{configure} command can
|
||||||
|
be used to enable the relational modules:
|
||||||
|
\begin{verbatim}
|
||||||
|
./configure --enable-odbc
|
||||||
|
\end{verbatim}
|
||||||
|
|
||||||
|
If you are planning to use Microsoft SQL Server with ODBC, you need to specify
|
||||||
|
it from the \term{configure} command before compilation:
|
||||||
|
\begin{verbatim}
|
||||||
|
./configure --enable-odbc --enable-mssql
|
||||||
|
\end{verbatim}
|
||||||
|
|
||||||
\subsubsection{Authentication against a relational database}
|
\subsubsection{Authentication against a relational database}
|
||||||
\label{sec:relationaldatabaseauth}
|
\label{sec:relationaldatabaseauth}
|
||||||
|
|
||||||
|
|
|
@ -100,7 +100,9 @@ Besides common \Jabber{} server features, \ejabberd{} comes with a wide range of
|
||||||
\item Native MySQL support.\new{}
|
\item Native MySQL support.\new{}
|
||||||
\item Native PostgreSQL support.
|
\item Native PostgreSQL support.
|
||||||
\item Mnesia.
|
\item Mnesia.
|
||||||
\item ODBC data storage support. \moreinfo{ --- ODBC requests can be load balanced between several connections.}
|
\item ODBC data storage support. \moreinfo{ --- ODBC requests can be load
|
||||||
|
balanced between several connections.}
|
||||||
|
\item Microsoft SQL Server support (via ODBC).\new{}
|
||||||
\end{itemize}
|
\end{itemize}
|
||||||
\item Authentication
|
\item Authentication
|
||||||
\begin{itemize}
|
\begin{itemize}
|
||||||
|
|
3963
src/configure
vendored
3963
src/configure
vendored
File diff suppressed because it is too large
Load Diff
|
@ -37,7 +37,7 @@ AC_MOD_ENABLE(odbc, no)
|
||||||
AC_MOD_ENABLE(ejabberd_zlib, yes)
|
AC_MOD_ENABLE(ejabberd_zlib, yes)
|
||||||
|
|
||||||
AC_ARG_ENABLE(roster_gateway_workaround,
|
AC_ARG_ENABLE(roster_gateway_workaround,
|
||||||
[ --enable-roster-gateway-workaround Turn on workaround for processing gateway subscriptions],
|
[ --enable-roster-gateway-workaround Turn on workaround for processing gateway subscriptions (default: no)],
|
||||||
[case "${enableval}" in
|
[case "${enableval}" in
|
||||||
yes) roster_gateway_workaround=true ;;
|
yes) roster_gateway_workaround=true ;;
|
||||||
no) roster_gateway_workaround=false ;;
|
no) roster_gateway_workaround=false ;;
|
||||||
|
@ -45,6 +45,15 @@ AC_ARG_ENABLE(roster_gateway_workaround,
|
||||||
esac],[roster_gateway_workaround=false])
|
esac],[roster_gateway_workaround=false])
|
||||||
AC_SUBST(roster_gateway_workaround)
|
AC_SUBST(roster_gateway_workaround)
|
||||||
|
|
||||||
|
AC_ARG_ENABLE(mssql,
|
||||||
|
[ --enable-mssql Use Microsoft SQL Server database (default: no, requires --enable-odbc)],
|
||||||
|
[case "${enableval}" in
|
||||||
|
yes) db_type=mssql ;;
|
||||||
|
no) db_type=generic ;;
|
||||||
|
*) AC_MSG_ERROR(bad value ${enableval} for --enable-mssql) ;;
|
||||||
|
esac],[db_type=generic])
|
||||||
|
AC_SUBST(db_type)
|
||||||
|
|
||||||
AC_CONFIG_FILES([Makefile
|
AC_CONFIG_FILES([Makefile
|
||||||
$make_mod_irc
|
$make_mod_irc
|
||||||
$make_mod_muc
|
$make_mod_muc
|
||||||
|
|
|
@ -46,6 +46,7 @@ start() ->
|
||||||
Version = "EJABBERD_VERSION = " ++ ?VERSION ++ "\n",
|
Version = "EJABBERD_VERSION = " ++ ?VERSION ++ "\n",
|
||||||
ExpatDir = "EXPAT_DIR = c:\\progra~1\\expat-1.95.7\n",
|
ExpatDir = "EXPAT_DIR = c:\\progra~1\\expat-1.95.7\n",
|
||||||
OpenSSLDir = "OPENSSL_DIR = c:\\progra~1\\OpenSSL\n",
|
OpenSSLDir = "OPENSSL_DIR = c:\\progra~1\\OpenSSL\n",
|
||||||
|
DBType = "DBTYPE = generic\n", %% 'generic' or 'mssql'
|
||||||
|
|
||||||
SSLDir = "SSLDIR = " ++ code:lib_dir("ssl") ++ "\n",
|
SSLDir = "SSLDIR = " ++ code:lib_dir("ssl") ++ "\n",
|
||||||
StdLibDir = "STDLIBDIR = " ++ code:lib_dir("stdlib") ++ "\n",
|
StdLibDir = "STDLIBDIR = " ++ code:lib_dir("stdlib") ++ "\n",
|
||||||
|
@ -58,6 +59,7 @@ start() ->
|
||||||
SSLDir ++
|
SSLDir ++
|
||||||
StdLibDir ++
|
StdLibDir ++
|
||||||
OpenSSLDir ++
|
OpenSSLDir ++
|
||||||
|
DBType ++
|
||||||
ExpatDir ++
|
ExpatDir ++
|
||||||
ExpatLib ++
|
ExpatLib ++
|
||||||
ExpatFlag ++
|
ExpatFlag ++
|
||||||
|
|
|
@ -57,10 +57,8 @@ check_password(User, Server, Password) ->
|
||||||
false;
|
false;
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:get_password(LServer, Username) of
|
||||||
["select password from users "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{selected, ["password"], [{Password}]} ->
|
{selected, ["password"], [{Password}]} ->
|
||||||
true;
|
true;
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -74,10 +72,8 @@ check_password(User, Server, Password, StreamID, Digest) ->
|
||||||
false;
|
false;
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:get_password(LServer, Username) of
|
||||||
["select password from users "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{selected, ["password"], [{Passwd}]} ->
|
{selected, ["password"], [{Passwd}]} ->
|
||||||
DigRes = if
|
DigRes = if
|
||||||
Digest /= "" ->
|
Digest /= "" ->
|
||||||
|
@ -103,11 +99,7 @@ set_password(User, Server, Password) ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
Pass = ejabberd_odbc:escape(Password),
|
Pass = ejabberd_odbc:escape(Password),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
catch ejabberd_odbc:sql_transaction(
|
catch odbc_queries:set_password_t(LServer, Username, Pass)
|
||||||
LServer,
|
|
||||||
[["delete from users where username='", Username ,"';"],
|
|
||||||
["insert into users(username, password) "
|
|
||||||
"values ('", Username, "', '", Pass, "');"]])
|
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
|
||||||
|
@ -118,10 +110,8 @@ try_register(User, Server, Password) ->
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
Pass = ejabberd_odbc:escape(Password),
|
Pass = ejabberd_odbc:escape(Password),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:add_user(LServer, Username, Pass) of
|
||||||
["insert into users(username, password) "
|
|
||||||
"values ('", Username, "', '", Pass, "');"]) of
|
|
||||||
{updated, 1} ->
|
{updated, 1} ->
|
||||||
{atomic, ok};
|
{atomic, ok};
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -134,9 +124,7 @@ dirty_get_registered_users() ->
|
||||||
|
|
||||||
get_vh_registered_users(Server) ->
|
get_vh_registered_users(Server) ->
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:list_users(LServer) of
|
||||||
LServer,
|
|
||||||
"select username from users") of
|
|
||||||
{selected, ["username"], Res} ->
|
{selected, ["username"], Res} ->
|
||||||
[{U, LServer} || {U} <- Res];
|
[{U, LServer} || {U} <- Res];
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -149,10 +137,8 @@ get_password(User, Server) ->
|
||||||
false;
|
false;
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:get_password(LServer, Username) of
|
||||||
["select password from users "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{selected, ["password"], [{Password}]} ->
|
{selected, ["password"], [{Password}]} ->
|
||||||
Password;
|
Password;
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -166,10 +152,8 @@ get_password_s(User, Server) ->
|
||||||
"";
|
"";
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:get_password(LServer, Username) of
|
||||||
["select password from users "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{selected, ["password"], [{Password}]} ->
|
{selected, ["password"], [{Password}]} ->
|
||||||
Password;
|
Password;
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -183,10 +167,8 @@ is_user_exists(User, Server) ->
|
||||||
false;
|
false;
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
case catch odbc_queries:get_password(LServer, Username) of
|
||||||
["select password from users "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{selected, ["password"], [{_Password}]} ->
|
{selected, ["password"], [{_Password}]} ->
|
||||||
true;
|
true;
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -200,9 +182,8 @@ remove_user(User, Server) ->
|
||||||
error;
|
error;
|
||||||
LUser ->
|
LUser ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
catch ejabberd_odbc:sql_query(
|
LServer = jlib:nameprep(Server),
|
||||||
jlib:nameprep(Server),
|
catch odbc_queries:del_user(LServer, Username),
|
||||||
["delete from users where username='", Username ,"';"]),
|
|
||||||
ejabberd_hooks:run(remove_user, jlib:nameprep(Server),
|
ejabberd_hooks:run(remove_user, jlib:nameprep(Server),
|
||||||
[User, Server])
|
[User, Server])
|
||||||
end.
|
end.
|
||||||
|
@ -216,12 +197,8 @@ remove_user(User, Server, Password) ->
|
||||||
Pass = ejabberd_odbc:escape(Password),
|
Pass = ejabberd_odbc:escape(Password),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
F = fun() ->
|
F = fun() ->
|
||||||
Result = ejabberd_odbc:sql_query_t(
|
Result = odbc_queries:del_user_return_password(
|
||||||
["select password from users where username='",
|
LServer, Username, Pass),
|
||||||
Username, "';"]),
|
|
||||||
ejabberd_odbc:sql_query_t(["delete from users "
|
|
||||||
"where username='", Username,
|
|
||||||
"' and password='", Pass, "';"]),
|
|
||||||
case Result of
|
case Result of
|
||||||
{selected, ["password"], [{Password}]} ->
|
{selected, ["password"], [{Password}]} ->
|
||||||
ejabberd_hooks:run(remove_user, jlib:nameprep(Server),
|
ejabberd_hooks:run(remove_user, jlib:nameprep(Server),
|
||||||
|
@ -233,6 +210,6 @@ remove_user(User, Server, Password) ->
|
||||||
not_allowed
|
not_allowed
|
||||||
end
|
end
|
||||||
end,
|
end,
|
||||||
{atomic, Result } = ejabberd_odbc:transaction(LServer, F),
|
{atomic, Result} = odbc_queries:transaction(LServer, F),
|
||||||
Result
|
Result
|
||||||
end.
|
end.
|
||||||
|
|
|
@ -95,10 +95,7 @@ process_sm_iq(From, To, #iq{type = Type, sub_el = SubEl} = IQ) ->
|
||||||
|
|
||||||
get_last(IQ, SubEl, LUser, LServer) ->
|
get_last(IQ, SubEl, LUser, LServer) ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_last(LServer, Username) of
|
||||||
LServer,
|
|
||||||
["select seconds, state from last "
|
|
||||||
"where username='", Username, "';"]) of
|
|
||||||
{'EXIT', _Reason} ->
|
{'EXIT', _Reason} ->
|
||||||
IQ#iq{type = error, sub_el = [SubEl, ?ERR_INTERNAL_SERVER_ERROR]};
|
IQ#iq{type = error, sub_el = [SubEl, ?ERR_INTERNAL_SERVER_ERROR]};
|
||||||
{selected, ["seconds","state"], []} ->
|
{selected, ["seconds","state"], []} ->
|
||||||
|
@ -131,16 +128,11 @@ store_last_info(User, Server, TimeStamp, Status) ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
Seconds = ejabberd_odbc:escape(integer_to_list(TimeStamp)),
|
Seconds = ejabberd_odbc:escape(integer_to_list(TimeStamp)),
|
||||||
State = ejabberd_odbc:escape(Status),
|
State = ejabberd_odbc:escape(Status),
|
||||||
%% MREMOND: I think this should be turn into a non transactional behaviour
|
odbc_queries:set_last_t(LServer, Username, Seconds, State).
|
||||||
ejabberd_odbc:sql_transaction(
|
|
||||||
LServer,
|
|
||||||
[["delete from last where username='", Username, "';"],
|
|
||||||
["insert into last(username, seconds, state) "
|
|
||||||
"values ('", Username, "', '", Seconds, "', '", State, "');"]]).
|
|
||||||
|
|
||||||
remove_user(User, Server) ->
|
remove_user(User, Server) ->
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
ejabberd_odbc:sql_query(LServer,
|
odbc_queries:del_last(LServer, Username).
|
||||||
["delete from last where username='", Username, "';"]).
|
|
||||||
|
|
|
@ -65,14 +65,9 @@ loop(Host) ->
|
||||||
ejabberd_odbc:escape(
|
ejabberd_odbc:escape(
|
||||||
lists:flatten(
|
lists:flatten(
|
||||||
xml:element_to_string(Packet))),
|
xml:element_to_string(Packet))),
|
||||||
["insert into spool(username, xml) "
|
odbc_queries:add_spool_sql(Username, XML)
|
||||||
"values ('", Username, "', '",
|
|
||||||
XML,
|
|
||||||
"');"]
|
|
||||||
end, Msgs),
|
end, Msgs),
|
||||||
case catch ejabberd_odbc:sql_transaction(
|
case catch odbc_queries:add_spool(Host, Query) of
|
||||||
Host,
|
|
||||||
Query) of
|
|
||||||
{'EXIT', Reason} ->
|
{'EXIT', Reason} ->
|
||||||
?ERROR_MSG("~p~n", [Reason]);
|
?ERROR_MSG("~p~n", [Reason]);
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -207,15 +202,7 @@ pop_offline_messages(Ls, User, Server) ->
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
EUser = ejabberd_odbc:escape(LUser),
|
EUser = ejabberd_odbc:escape(LUser),
|
||||||
F = fun() ->
|
case odbc_queries:get_and_del_spool_msg_t(LServer, EUser) of
|
||||||
Result = ejabberd_odbc:sql_query_t(
|
|
||||||
["select username, xml from spool where username='", EUser, "'"
|
|
||||||
" order by seq;"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["delete from spool where username='", EUser, "';"]),
|
|
||||||
Result
|
|
||||||
end,
|
|
||||||
case ejabberd_odbc:sql_transaction(LServer,F) of
|
|
||||||
{atomic, {selected, ["username","xml"], Rs}} ->
|
{atomic, {selected, ["username","xml"], Rs}} ->
|
||||||
Ls ++ lists:flatmap(
|
Ls ++ lists:flatmap(
|
||||||
fun({_, XML}) ->
|
fun({_, XML}) ->
|
||||||
|
@ -245,7 +232,5 @@ remove_user(User, Server) ->
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
ejabberd_odbc:sql_query(
|
odbc_queries:del_spool_msg(LServer, Username).
|
||||||
LServer,
|
|
||||||
["delete from spool where username='", Username, "';"]).
|
|
||||||
|
|
||||||
|
|
|
@ -122,20 +122,13 @@ process_iq_get(From, To, #iq{sub_el = SubEl} = IQ) ->
|
||||||
|
|
||||||
get_user_roster(Acc, {LUser, LServer}) ->
|
get_user_roster(Acc, {LUser, LServer}) ->
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_roster(LServer, Username) of
|
||||||
LServer,
|
|
||||||
["select username, jid, nick, subscription, ask, "
|
|
||||||
"askmessage, server, subscribe, type from rosterusers "
|
|
||||||
"where username='", Username, "'"]) of
|
|
||||||
{selected, ["username", "jid", "nick", "subscription", "ask",
|
{selected, ["username", "jid", "nick", "subscription", "ask",
|
||||||
"askmessage", "server", "subscribe", "type"],
|
"askmessage", "server", "subscribe", "type"],
|
||||||
Items} when is_list(Items) ->
|
Items} when is_list(Items) ->
|
||||||
JIDGroups = case catch ejabberd_odbc:sql_query(
|
JIDGroups = case catch odbc_queries:get_roster_jid_groups(LServer, Username) of
|
||||||
LServer,
|
{selected, ["jid","grp"], JGrps}
|
||||||
["select jid, grp from rostergroups "
|
when is_list(JGrps) ->
|
||||||
"where username='", Username, "'"]) of
|
|
||||||
{selected, ["jid","grp"],
|
|
||||||
JGrps} when is_list(JGrps) ->
|
|
||||||
JGrps;
|
JGrps;
|
||||||
_ ->
|
_ ->
|
||||||
[]
|
[]
|
||||||
|
@ -148,10 +141,11 @@ get_user_roster(Acc, {LUser, LServer}) ->
|
||||||
R ->
|
R ->
|
||||||
SJID = jlib:jid_to_string(R#roster.jid),
|
SJID = jlib:jid_to_string(R#roster.jid),
|
||||||
Groups = lists:flatmap(
|
Groups = lists:flatmap(
|
||||||
fun({S, G}) when S == SJID ->
|
fun({S, G}) ->
|
||||||
[G];
|
case jlib:jid_tolower(S) of
|
||||||
(_) ->
|
SJID -> [G];
|
||||||
[]
|
_ -> []
|
||||||
|
end
|
||||||
end, JIDGroups),
|
end, JIDGroups),
|
||||||
[R#roster{groups = Groups}]
|
[R#roster{groups = Groups}]
|
||||||
end
|
end
|
||||||
|
@ -216,13 +210,7 @@ process_item_set(From, To, {xmlelement, _Name, Attrs, Els}) ->
|
||||||
{selected,
|
{selected,
|
||||||
["username", "jid", "nick", "subscription",
|
["username", "jid", "nick", "subscription",
|
||||||
"ask", "askmessage", "server", "subscribe", "type"],
|
"ask", "askmessage", "server", "subscribe", "type"],
|
||||||
Res} =
|
Res} = odbc_queries:get_roster_by_jid(LServer, Username, SJID),
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["select username, jid, nick, subscription, "
|
|
||||||
"ask, askmessage, server, subscribe, type "
|
|
||||||
"from rosterusers "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SJID, "'"]),
|
|
||||||
Item = case Res of
|
Item = case Res of
|
||||||
[] ->
|
[] ->
|
||||||
#roster{usj = {LUser, LServer, LJID},
|
#roster{usj = {LUser, LServer, LJID},
|
||||||
|
@ -239,39 +227,11 @@ process_item_set(From, To, {xmlelement, _Name, Attrs, Els}) ->
|
||||||
Item2 = process_item_els(Item1, Els),
|
Item2 = process_item_els(Item1, Els),
|
||||||
case Item2#roster.subscription of
|
case Item2#roster.subscription of
|
||||||
remove ->
|
remove ->
|
||||||
ejabberd_odbc:sql_query_t(
|
odbc_queries:del_roster(LServer, Username, SJID);
|
||||||
["delete from rosterusers "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["delete from rostergroups "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]);
|
|
||||||
_ ->
|
_ ->
|
||||||
ItemVals = record_to_string(Item2),
|
ItemVals = record_to_string(Item2),
|
||||||
ItemGroups = groups_to_string(Item2),
|
ItemGroups = groups_to_string(Item2),
|
||||||
ejabberd_odbc:sql_query_t(
|
odbc_queries:update_roster(LServer, Username, SJID, ItemVals, ItemGroups)
|
||||||
["delete from rosterusers "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["insert into rosterusers("
|
|
||||||
" username, jid, nick, "
|
|
||||||
" subscription, ask, "
|
|
||||||
" askmessage, server, "
|
|
||||||
" subscribe, type) "
|
|
||||||
" values ", ItemVals, ";"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["delete from rostergroups "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]),
|
|
||||||
lists:foreach(fun(ItemGroup) ->
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["insert into rostergroups("
|
|
||||||
" username, jid, grp) "
|
|
||||||
" values ", ItemGroup, ";"])
|
|
||||||
end,
|
|
||||||
ItemGroups)
|
|
||||||
end,
|
end,
|
||||||
%% If the item exist in shared roster, take the
|
%% If the item exist in shared roster, take the
|
||||||
%% subscription information from there:
|
%% subscription information from there:
|
||||||
|
@ -279,7 +239,7 @@ process_item_set(From, To, {xmlelement, _Name, Attrs, Els}) ->
|
||||||
LServer, Item2, [LServer]),
|
LServer, Item2, [LServer]),
|
||||||
{Item, Item3}
|
{Item, Item3}
|
||||||
end,
|
end,
|
||||||
case ejabberd_odbc:sql_transaction(LServer, F) of
|
case odbc_queries:sql_transaction(LServer, F) of
|
||||||
{atomic, {OldItem, Item}} ->
|
{atomic, {OldItem, Item}} ->
|
||||||
push_item(User, LServer, To, Item),
|
push_item(User, LServer, To, Item),
|
||||||
case Item#roster.subscription of
|
case Item#roster.subscription of
|
||||||
|
@ -411,11 +371,7 @@ get_subscription_lists(_, User, Server) ->
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_roster(LServer, Username) of
|
||||||
LServer,
|
|
||||||
["select username, jid, nick, subscription, ask, "
|
|
||||||
"askmessage, server, subscribe, type from rosterusers "
|
|
||||||
"where username='", Username, "'"]) of
|
|
||||||
{selected, ["username", "jid", "nick", "subscription", "ask",
|
{selected, ["username", "jid", "nick", "subscription", "ask",
|
||||||
"askmessage", "server", "subscribe", "type"],
|
"askmessage", "server", "subscribe", "type"],
|
||||||
Items} when is_list(Items) ->
|
Items} when is_list(Items) ->
|
||||||
|
@ -460,22 +416,14 @@ process_subscription(Direction, User, Server, JID1, Type, Reason) ->
|
||||||
SJID = ejabberd_odbc:escape(jlib:jid_to_string(LJID)),
|
SJID = ejabberd_odbc:escape(jlib:jid_to_string(LJID)),
|
||||||
F = fun() ->
|
F = fun() ->
|
||||||
Item =
|
Item =
|
||||||
case ejabberd_odbc:sql_query_t(
|
case odbc_queries:get_roster_by_jid(LServer, Username, SJID) of
|
||||||
["select username, jid, nick, subscription, ask, "
|
|
||||||
"askmessage, server, subscribe, type "
|
|
||||||
"from rosterusers "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SJID, "';"]) of
|
|
||||||
{selected,
|
{selected,
|
||||||
["username", "jid", "nick", "subscription", "ask",
|
["username", "jid", "nick", "subscription", "ask",
|
||||||
"askmessage", "server", "subscribe", "type"],
|
"askmessage", "server", "subscribe", "type"],
|
||||||
[I]} ->
|
[I]} ->
|
||||||
R = raw_to_record(LServer, I),
|
R = raw_to_record(LServer, I),
|
||||||
Groups =
|
Groups =
|
||||||
case ejabberd_odbc:sql_query_t(
|
case odbc_queries:get_roster_groups(LServer, Username, SJID) of
|
||||||
["select grp from rostergroups "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SJID, "';"]) of
|
|
||||||
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
||||||
[JGrp || {JGrp} <- JGrps];
|
[JGrp || {JGrp} <- JGrps];
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -521,21 +469,11 @@ process_subscription(Direction, User, Server, JID1, Type, Reason) ->
|
||||||
ask = Pending,
|
ask = Pending,
|
||||||
askmessage = AskMessage},
|
askmessage = AskMessage},
|
||||||
ItemVals = record_to_string(NewItem),
|
ItemVals = record_to_string(NewItem),
|
||||||
ejabberd_odbc:sql_query_t(
|
odbc_queries:roster_subscribe(LServer, Username, SJID, ItemVals),
|
||||||
["delete from rosterusers "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["insert into rosterusers("
|
|
||||||
" username, jid, nick, "
|
|
||||||
" subscription, ask, "
|
|
||||||
" askmessage, server, subscribe, "
|
|
||||||
" type) "
|
|
||||||
" values ", ItemVals, ";"]),
|
|
||||||
{{push, NewItem}, AutoReply}
|
{{push, NewItem}, AutoReply}
|
||||||
end
|
end
|
||||||
end,
|
end,
|
||||||
case ejabberd_odbc:sql_transaction(LServer, F) of
|
case odbc_queries:sql_transaction(LServer, F) of
|
||||||
{atomic, {Push, AutoReply}} ->
|
{atomic, {Push, AutoReply}} ->
|
||||||
case AutoReply of
|
case AutoReply of
|
||||||
none ->
|
none ->
|
||||||
|
@ -662,16 +600,7 @@ remove_user(User, Server) ->
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
ejabberd_odbc:sql_transaction(
|
odbc_queries:del_user_roster_t(LServer, Username),
|
||||||
LServer,
|
|
||||||
fun() ->
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["delete from rosterusers "
|
|
||||||
" where username='", Username, "';"]),
|
|
||||||
ejabberd_odbc:sql_query_t(
|
|
||||||
["delete from rostergroups "
|
|
||||||
" where username='", Username, "';"])
|
|
||||||
end),
|
|
||||||
ok.
|
ok.
|
||||||
|
|
||||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||||
|
@ -680,7 +609,7 @@ set_items(User, Server, SubEl) ->
|
||||||
{xmlelement, _Name, _Attrs, Els} = SubEl,
|
{xmlelement, _Name, _Attrs, Els} = SubEl,
|
||||||
LUser = jlib:nodeprep(User),
|
LUser = jlib:nodeprep(User),
|
||||||
LServer = jlib:nameprep(Server),
|
LServer = jlib:nameprep(Server),
|
||||||
catch ejabberd_odbc:transaction(
|
catch odbc_queries:transaction(
|
||||||
LServer,
|
LServer,
|
||||||
lists:map(fun(El) ->
|
lists:map(fun(El) ->
|
||||||
process_item_set_t(LUser, LServer, El)
|
process_item_set_t(LUser, LServer, El)
|
||||||
|
@ -703,31 +632,11 @@ process_item_set_t(LUser, LServer, {xmlelement, _Name, Attrs, Els}) ->
|
||||||
Item2 = process_item_els(Item1, Els),
|
Item2 = process_item_els(Item1, Els),
|
||||||
case Item2#roster.subscription of
|
case Item2#roster.subscription of
|
||||||
remove ->
|
remove ->
|
||||||
[["delete from rosterusers "
|
odbc_queries:del_roster_sql(Username, SJID);
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"],
|
|
||||||
["delete from rostergroups "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"]];
|
|
||||||
_ ->
|
_ ->
|
||||||
ItemVals = record_to_string(Item1),
|
ItemVals = record_to_string(Item1),
|
||||||
ItemGroups = groups_to_string(Item2),
|
ItemGroups = groups_to_string(Item2),
|
||||||
[["delete from rosterusers "
|
odbc_queries:update_roster_sql(Username, SJID, ItemVals, ItemGroups)
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"],
|
|
||||||
["insert into rosterusers("
|
|
||||||
" username, jid, nick, "
|
|
||||||
" subscription, ask, "
|
|
||||||
" askmessage, server, subscribe, "
|
|
||||||
" type) "
|
|
||||||
" values ", ItemVals, ";"],
|
|
||||||
["delete from rostergroups "
|
|
||||||
" where username='", Username, "' "
|
|
||||||
" and jid='", SJID, "';"],
|
|
||||||
[["insert into rostergroups("
|
|
||||||
" username, jid, grp) "
|
|
||||||
" values ", ItemGroup, ";"] ||
|
|
||||||
ItemGroup <- ItemGroups]]
|
|
||||||
end
|
end
|
||||||
end;
|
end;
|
||||||
process_item_set_t(_LUser, _LServer, _) ->
|
process_item_set_t(_LUser, _LServer, _) ->
|
||||||
|
@ -773,34 +682,24 @@ process_item_attrs_ws(Item, [{Attr, Val} | Attrs]) ->
|
||||||
process_item_attrs_ws(Item, []) ->
|
process_item_attrs_ws(Item, []) ->
|
||||||
Item.
|
Item.
|
||||||
|
|
||||||
|
|
||||||
get_in_pending_subscriptions(Ls, User, Server) ->
|
get_in_pending_subscriptions(Ls, User, Server) ->
|
||||||
JID = jlib:make_jid(User, Server, ""),
|
JID = jlib:make_jid(User, Server, ""),
|
||||||
LUser = JID#jid.luser,
|
LUser = JID#jid.luser,
|
||||||
LServer = JID#jid.lserver,
|
LServer = JID#jid.lserver,
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_roster(LServer, Username) of
|
||||||
LServer,
|
|
||||||
["select username, jid, nick, subscription, ask, "
|
|
||||||
"askmessage, server, subscribe, type from rosterusers "
|
|
||||||
"where username='", Username, "'"]) of
|
|
||||||
{selected, ["username", "jid", "nick", "subscription", "ask",
|
{selected, ["username", "jid", "nick", "subscription", "ask",
|
||||||
"askmessage", "server", "subscribe", "type"],
|
"askmessage", "server", "subscribe", "type"],
|
||||||
Items} when is_list(Items) ->
|
Items} when is_list(Items) ->
|
||||||
Ls ++ lists:map(
|
Ls ++ lists:map(
|
||||||
fun(R) ->
|
fun(R) ->
|
||||||
Message = R#roster.askmessage,
|
Message = R#roster.askmessage,
|
||||||
Status = if is_binary(Message) ->
|
|
||||||
binary_to_list(Message);
|
|
||||||
true ->
|
|
||||||
""
|
|
||||||
end,
|
|
||||||
{xmlelement, "presence",
|
{xmlelement, "presence",
|
||||||
[{"from", jlib:jid_to_string(R#roster.jid)},
|
[{"from", jlib:jid_to_string(R#roster.jid)},
|
||||||
{"to", jlib:jid_to_string(JID)},
|
{"to", jlib:jid_to_string(JID)},
|
||||||
{"type", "subscribe"}],
|
{"type", "subscribe"}],
|
||||||
[{xmlelement, "status", [],
|
[{xmlelement, "status", [],
|
||||||
[{xmlcdata, Status}]}]}
|
[{xmlcdata, Message}]}]}
|
||||||
end,
|
end,
|
||||||
lists:flatmap(
|
lists:flatmap(
|
||||||
fun(I) ->
|
fun(I) ->
|
||||||
|
@ -825,11 +724,7 @@ get_jid_info(_, User, Server, JID) ->
|
||||||
LJID = jlib:jid_tolower(JID),
|
LJID = jlib:jid_tolower(JID),
|
||||||
Username = ejabberd_odbc:escape(LUser),
|
Username = ejabberd_odbc:escape(LUser),
|
||||||
SJID = ejabberd_odbc:escape(jlib:jid_to_string(LJID)),
|
SJID = ejabberd_odbc:escape(jlib:jid_to_string(LJID)),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_subscription(LServer, Username, SJID) of
|
||||||
LServer,
|
|
||||||
["select subscription from rosterusers "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SJID, "'"]) of
|
|
||||||
{selected, ["subscription"], [{SSubscription}]} ->
|
{selected, ["subscription"], [{SSubscription}]} ->
|
||||||
Subscription = case SSubscription of
|
Subscription = case SSubscription of
|
||||||
"B" -> both;
|
"B" -> both;
|
||||||
|
@ -837,11 +732,7 @@ get_jid_info(_, User, Server, JID) ->
|
||||||
"F" -> from;
|
"F" -> from;
|
||||||
_ -> none
|
_ -> none
|
||||||
end,
|
end,
|
||||||
Groups = case catch ejabberd_odbc:sql_query(
|
Groups = case catch odbc_queries:get_roster_group_by_jid(LServer, Username, SJID) of
|
||||||
LServer,
|
|
||||||
["select grp from rostergroups "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SJID, "'"]) of
|
|
||||||
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
||||||
[JGrp || {JGrp} <- JGrps];
|
[JGrp || {JGrp} <- JGrps];
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -855,11 +746,7 @@ get_jid_info(_, User, Server, JID) ->
|
||||||
{none, []};
|
{none, []};
|
||||||
true ->
|
true ->
|
||||||
SRJID = ejabberd_odbc:escape(jlib:jid_to_string(LRJID)),
|
SRJID = ejabberd_odbc:escape(jlib:jid_to_string(LRJID)),
|
||||||
case catch ejabberd_odbc:sql_query(
|
case catch odbc_queries:get_subscription(LServer, Username, SRJID) of
|
||||||
LServer,
|
|
||||||
["select subscription from rosterusers "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SRJID, "'"]) of
|
|
||||||
{selected, ["subscription"], [{SSubscription}]} ->
|
{selected, ["subscription"], [{SSubscription}]} ->
|
||||||
Subscription = case SSubscription of
|
Subscription = case SSubscription of
|
||||||
"B" -> both;
|
"B" -> both;
|
||||||
|
@ -867,11 +754,7 @@ get_jid_info(_, User, Server, JID) ->
|
||||||
"F" -> from;
|
"F" -> from;
|
||||||
_ -> none
|
_ -> none
|
||||||
end,
|
end,
|
||||||
Groups = case catch ejabberd_odbc:sql_query(
|
Groups = case catch odbc_queries:get_rostergroup_by_jid(LServer, Username, SRJID) of
|
||||||
LServer,
|
|
||||||
["select grp from rostergroups "
|
|
||||||
"where username='", Username, "' "
|
|
||||||
"and jid='", SRJID, "'"]) of
|
|
||||||
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
{selected, ["grp"], JGrps} when is_list(JGrps) ->
|
||||||
[JGrp || {JGrp} <- JGrps];
|
[JGrp || {JGrp} <- JGrps];
|
||||||
_ ->
|
_ ->
|
||||||
|
@ -939,22 +822,26 @@ record_to_string(#roster{us = {User, _Server},
|
||||||
in -> "I";
|
in -> "I";
|
||||||
none -> "N"
|
none -> "N"
|
||||||
end,
|
end,
|
||||||
["("
|
["'", Username, "',"
|
||||||
"'", Username, "',"
|
|
||||||
"'", SJID, "',"
|
"'", SJID, "',"
|
||||||
"'", Nick, "',"
|
"'", Nick, "',"
|
||||||
"'", SSubscription, "',"
|
"'", SSubscription, "',"
|
||||||
"'", SAsk, "',"
|
"'", SAsk, "',"
|
||||||
"'", AskMessage, "',"
|
"'", AskMessage, "',"
|
||||||
"'N', '', 'item')"].
|
"'N', '', 'item'"].
|
||||||
|
|
||||||
groups_to_string(#roster{us = {User, _Server},
|
groups_to_string(#roster{us = {User, _Server},
|
||||||
jid = JID,
|
jid = JID,
|
||||||
groups = Groups}) ->
|
groups = Groups}) ->
|
||||||
Username = ejabberd_odbc:escape(User),
|
Username = ejabberd_odbc:escape(User),
|
||||||
SJID = ejabberd_odbc:escape(jlib:jid_to_string(jlib:jid_tolower(JID))),
|
SJID = ejabberd_odbc:escape(jlib:jid_to_string(jlib:jid_tolower(JID))),
|
||||||
[["("
|
|
||||||
"'", Username, "',"
|
%% Empty groups do not need to be converted to string to be inserted in
|
||||||
"'", SJID, "',"
|
%% the database
|
||||||
"'", ejabberd_odbc:escape(Group), "')"] || Group <- Groups].
|
lists:foldl(fun([], Acc) -> Acc;
|
||||||
|
(Group, Acc) ->
|
||||||
|
String = ["'", Username, "',"
|
||||||
|
"'", SJID, "',"
|
||||||
|
"'", ejabberd_odbc:escape(Group), "'"],
|
||||||
|
[String|Acc] end, [], Groups).
|
||||||
|
|
||||||
|
|
|
@ -13,12 +13,13 @@ OUTDIR = ..
|
||||||
EFLAGS = -I .. -pz ..
|
EFLAGS = -I .. -pz ..
|
||||||
OBJS = \
|
OBJS = \
|
||||||
$(OUTDIR)/ejabberd_odbc.beam \
|
$(OUTDIR)/ejabberd_odbc.beam \
|
||||||
$(OUTDIR)/ejabberd_odbc_sup.beam
|
$(OUTDIR)/ejabberd_odbc_sup.beam \
|
||||||
|
$(OUTDIR)/odbc_queries.beam
|
||||||
|
|
||||||
all: $(OBJS)
|
all: $(OBJS)
|
||||||
|
|
||||||
$(OUTDIR)/%.beam: %.erl
|
$(OUTDIR)/%.beam: %.erl
|
||||||
@ERLC@ -W $(EFLAGS) -o $(OUTDIR) $<
|
@ERLC@ -W $(EFLAGS) -D@db_type@ -o $(OUTDIR) $<
|
||||||
|
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
|
|
|
@ -6,7 +6,8 @@ EFLAGS = -I .. -pz ..
|
||||||
|
|
||||||
OBJS = \
|
OBJS = \
|
||||||
$(OUTDIR)\ejabberd_odbc.beam \
|
$(OUTDIR)\ejabberd_odbc.beam \
|
||||||
$(OUTDIR)\ejabberd_odbc_sup.beam
|
$(OUTDIR)\ejabberd_odbc_sup.beam \
|
||||||
|
$(OUTDIR)\odbc_queries.beam
|
||||||
|
|
||||||
ALL : $(OBJS)
|
ALL : $(OBJS)
|
||||||
|
|
||||||
|
@ -18,3 +19,7 @@ $(OUTDIR)\ejabberd_odbc.beam : ejabberd_odbc.erl
|
||||||
|
|
||||||
$(OUTDIR)\ejabberd_odbc_sup.beam : ejabberd_odbc_sup.erl
|
$(OUTDIR)\ejabberd_odbc_sup.beam : ejabberd_odbc_sup.erl
|
||||||
erlc -W $(EFLAGS) -o $(OUTDIR) ejabberd_odbc_sup.erl
|
erlc -W $(EFLAGS) -o $(OUTDIR) ejabberd_odbc_sup.erl
|
||||||
|
|
||||||
|
$(OUTDIR)\odbc_queries.beam : odbc_queries.erl
|
||||||
|
erlc -W $(EFLAGS) -o $(OUTDIR) -D$(DBTYPE) odbc_queries.erl
|
||||||
|
|
||||||
|
|
|
@ -87,16 +87,7 @@ sql_query_t(Query) ->
|
||||||
|
|
||||||
%% Escape character that will confuse an SQL engine
|
%% Escape character that will confuse an SQL engine
|
||||||
escape(S) when is_list(S) ->
|
escape(S) when is_list(S) ->
|
||||||
[escape(C) || C <- S];
|
[odbc_queries:escape(C) || C <- S].
|
||||||
escape($\0) -> "\\0";
|
|
||||||
escape($\n) -> "\\n";
|
|
||||||
escape($\t) -> "\\t";
|
|
||||||
escape($\b) -> "\\b";
|
|
||||||
escape($\r) -> "\\r";
|
|
||||||
escape($') -> "\\'";
|
|
||||||
escape($") -> "\\\"";
|
|
||||||
escape($\\) -> "\\\\";
|
|
||||||
escape(C) -> C.
|
|
||||||
|
|
||||||
%% Escape character that will confuse an SQL engine
|
%% Escape character that will confuse an SQL engine
|
||||||
%% Percent and underscore only need to be escaped for pattern matching like
|
%% Percent and underscore only need to be escaped for pattern matching like
|
||||||
|
@ -105,7 +96,7 @@ escape_like(S) when is_list(S) ->
|
||||||
[escape_like(C) || C <- S];
|
[escape_like(C) || C <- S];
|
||||||
escape_like($%) -> "\\%";
|
escape_like($%) -> "\\%";
|
||||||
escape_like($_) -> "\\_";
|
escape_like($_) -> "\\_";
|
||||||
escape_like(C) -> escape(C).
|
escape_like(C) -> odbc_queries:escape(C).
|
||||||
|
|
||||||
|
|
||||||
%%%----------------------------------------------------------------------
|
%%%----------------------------------------------------------------------
|
||||||
|
|
901
src/odbc/mssql.sql
Normal file
901
src/odbc/mssql.sql
Normal file
|
@ -0,0 +1,901 @@
|
||||||
|
SET ANSI_NULLS ON
|
||||||
|
GO
|
||||||
|
SET QUOTED_IDENTIFIER ON
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'autoclose', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'bulkcopy', N'true'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'trunc. log', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'torn page detection', N'true'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'read only', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'dbo use', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'single', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'autoshrink', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'ANSI null default', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'recursive triggers', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'ANSI nulls', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'concat null yields null', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'cursor close on commit', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'default to local cursor', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'quoted identifier', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'ANSI warnings', N'false'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'auto create statistics', N'true'
|
||||||
|
GO
|
||||||
|
|
||||||
|
exec sp_dboption N'ejabberd', N'auto update statistics', N'true'
|
||||||
|
GO
|
||||||
|
|
||||||
|
use [ejabberd]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[last]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[last]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[rostergroups]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[rostergroups]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[rosterusers]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[rosterusers]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[spool]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[spool]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[users]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[users]
|
||||||
|
GO
|
||||||
|
|
||||||
|
if exists (select * from dbo.sysobjects where id = object_id(N'[dbo].[vcard]') and OBJECTPROPERTY(id, N'IsUserTable') = 1)
|
||||||
|
drop table [dbo].[vcard]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[last] (
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[seconds] [varchar] (50) NOT NULL ,
|
||||||
|
[state] [varchar] (100) NULL ,
|
||||||
|
[Modify_Date] [datetime] NULL
|
||||||
|
) ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[rostergroups] (
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[jid] [varchar] (250) NOT NULL ,
|
||||||
|
[grp] [varchar] (100) NOT NULL
|
||||||
|
) ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[rosterusers] (
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[jid] [varchar] (250) NOT NULL ,
|
||||||
|
[nick] [varchar] (50) NULL ,
|
||||||
|
[subscription] [char] (1) NOT NULL ,
|
||||||
|
[ask] [char] (1) NOT NULL ,
|
||||||
|
[askmessage] [varchar] (250) NULL ,
|
||||||
|
[server] [char] (1) NOT NULL ,
|
||||||
|
[subscribe] [varchar] (200) NULL ,
|
||||||
|
[type] [varchar] (50) NULL
|
||||||
|
) ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[spool] (
|
||||||
|
[id] [numeric](19, 0) IDENTITY (1, 1) NOT NULL ,
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[xml] [text] NULL ,
|
||||||
|
[notifyprocessed] [bit] NULL ,
|
||||||
|
[created] [datetime] NULL ,
|
||||||
|
[MustDelete] [bit] NULL
|
||||||
|
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[users] (
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[password] [varchar] (50) NOT NULL ,
|
||||||
|
[created] [datetime] NULL
|
||||||
|
) ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE TABLE [dbo].[vcard] (
|
||||||
|
[username] [varchar] (250) NOT NULL ,
|
||||||
|
[full_name] [varchar] (250) NULL ,
|
||||||
|
[first_name] [varchar] (50) NULL ,
|
||||||
|
[last_name] [varchar] (50) NULL ,
|
||||||
|
[nick_name] [varchar] (50) NULL ,
|
||||||
|
[url] [varchar] (1024) NULL ,
|
||||||
|
[address1] [varchar] (50) NULL ,
|
||||||
|
[address2] [varchar] (50) NULL ,
|
||||||
|
[locality] [varchar] (50) NULL ,
|
||||||
|
[region] [varchar] (50) NULL ,
|
||||||
|
[pcode] [varchar] (50) NULL ,
|
||||||
|
[country] [varchar] (50) NULL ,
|
||||||
|
[telephone] [varchar] (50) NULL ,
|
||||||
|
[email] [varchar] (250) NULL ,
|
||||||
|
[orgname] [varchar] (50) NULL ,
|
||||||
|
[orgunit] [varchar] (50) NULL ,
|
||||||
|
[title] [varchar] (50) NULL ,
|
||||||
|
[role] [varchar] (50) NULL ,
|
||||||
|
[b_day] [datetime] NULL ,
|
||||||
|
[descr] [varchar] (500) NULL
|
||||||
|
) ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[last] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [PK_last] PRIMARY KEY CLUSTERED
|
||||||
|
(
|
||||||
|
[username]
|
||||||
|
) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[rostergroups] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [PK_rostergroups] PRIMARY KEY CLUSTERED
|
||||||
|
(
|
||||||
|
[username],
|
||||||
|
[jid],
|
||||||
|
[grp]
|
||||||
|
) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[spool] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [PK_spool] PRIMARY KEY CLUSTERED
|
||||||
|
(
|
||||||
|
[username],
|
||||||
|
[id]
|
||||||
|
) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[users] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [PK_users] PRIMARY KEY CLUSTERED
|
||||||
|
(
|
||||||
|
[username]
|
||||||
|
) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[vcard] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [PK_vcard] PRIMARY KEY CLUSTERED
|
||||||
|
(
|
||||||
|
[username]
|
||||||
|
) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE CLUSTERED INDEX [IX_rosterusers_user] ON [dbo].[rosterusers]([username]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[last] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [DF_last_updated] DEFAULT (getdate()) FOR [Modify_Date]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[spool] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [DF_spool_notifyprocessed] DEFAULT (0) FOR [notifyprocessed],
|
||||||
|
CONSTRAINT [DF_spool_created] DEFAULT (getdate()) FOR [created],
|
||||||
|
CONSTRAINT [DF_spool_MustDelete] DEFAULT (0) FOR [MustDelete]
|
||||||
|
GO
|
||||||
|
|
||||||
|
ALTER TABLE [dbo].[users] WITH NOCHECK ADD
|
||||||
|
CONSTRAINT [DF_users_created] DEFAULT (getdate()) FOR [created]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IX_rostergroups_jid] ON [dbo].[rostergroups]([jid]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IX_rostergroups_user] ON [dbo].[rostergroups]([username]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IX_rosterusers_jid] ON [dbo].[rosterusers]([username], [jid]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IX_spool_user] ON [dbo].[spool]([username]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IX_spool_process] ON [dbo].[spool]([created], [notifyprocessed]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IK_Spool_Del] ON [dbo].[spool]([MustDelete]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
CREATE INDEX [IK_Spool_Created] ON [dbo].[spool]([created]) WITH FILLFACTOR = 90 ON [PRIMARY]
|
||||||
|
GO
|
||||||
|
|
||||||
|
/*********************************************************/
|
||||||
|
/** These store procedures are for use with ejabberd **/
|
||||||
|
/** 1.1 and Microsoft Sql Server 2000 **/
|
||||||
|
/** **/
|
||||||
|
/** The stored procedures reduce the need to sql **/
|
||||||
|
/** compilation of the database and also allow for also **/
|
||||||
|
/** provide each of database integration. The store **/
|
||||||
|
/** procedure have been optimized to increase database **/
|
||||||
|
/** performance and a reduction of 80% in CPU was **/
|
||||||
|
/** achive over the use of standard sql. **/
|
||||||
|
/*********************************************************/
|
||||||
|
|
||||||
|
/****** Object: StoredProcedure [dbo].[add_roster] ******/
|
||||||
|
/** Add or update user entries in the roster **/
|
||||||
|
/*********************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[add_roster]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250),
|
||||||
|
@Nick varchar(50),
|
||||||
|
@Subscription char(1),
|
||||||
|
@Ask char(1),
|
||||||
|
@AskMessage varchar(250),
|
||||||
|
@Server char(1),
|
||||||
|
@Subscribe varchar(200),
|
||||||
|
@Type varchar(50),
|
||||||
|
@Grp varchar(100)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
BEGIN TRANSACTION
|
||||||
|
--- Update Roster if user exist else add roster item
|
||||||
|
IF EXISTS (SELECT username FROM rosterusers WITH (NOLOCK) WHERE rosterusers.username=@Username AND rosterusers.jid=@JID)
|
||||||
|
BEGIN
|
||||||
|
UPDATE rosterusers
|
||||||
|
SET rosterusers.username=@Username,
|
||||||
|
rosterusers.jid=@JID,
|
||||||
|
rosterusers.nick=@Nick,
|
||||||
|
rosterusers.subscription=@Subscription,
|
||||||
|
rosterusers.ask=@Ask,
|
||||||
|
rosterusers.askmessage=@AskMessage,
|
||||||
|
rosterusers.server=@Server,
|
||||||
|
rosterusers.subscribe=@Subscribe,
|
||||||
|
rosterusers.type=@Type
|
||||||
|
WHERE (rosterusers.username=@Username) AND (rosterusers.jid=@JID);
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO rosterusers
|
||||||
|
( rosterusers.username,
|
||||||
|
rosterusers.jid,
|
||||||
|
rosterusers.nick,
|
||||||
|
rosterusers.subscription,
|
||||||
|
rosterusers.ask,
|
||||||
|
rosterusers.askmessage,
|
||||||
|
rosterusers.server,
|
||||||
|
rosterusers.subscribe,
|
||||||
|
rosterusers.type
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@JID,
|
||||||
|
@Nick,
|
||||||
|
@Subscription,
|
||||||
|
@Ask,
|
||||||
|
@AskMessage,
|
||||||
|
@Server,
|
||||||
|
@Subscribe,
|
||||||
|
@Type
|
||||||
|
);
|
||||||
|
END
|
||||||
|
|
||||||
|
--- Update Roster Groups if exist else add group entry
|
||||||
|
IF NOT EXISTS (SELECT username FROM rostergroups WITH (NOLOCK) WHERE rostergroups.username=@Username AND rostergroups.jid=@JID AND rostergroups.grp=@Grp)
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO rostergroups
|
||||||
|
( rostergroups.username,
|
||||||
|
rostergroups.jid,
|
||||||
|
rostergroups.grp
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@JID,
|
||||||
|
@Grp
|
||||||
|
);
|
||||||
|
END
|
||||||
|
|
||||||
|
COMMIT
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[add_roster_group] ******/
|
||||||
|
/** Add or update user group entries in the roster groups **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[add_roster_group]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250),
|
||||||
|
@Grp varchar(100)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
--- Update Roster Groups if exist else add group
|
||||||
|
IF NOT EXISTS (SELECT username FROM rostergroups WHERE rostergroups.username=@Username AND rostergroups.jid=@JID AND rostergroups.grp=@Grp)
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO rostergroups
|
||||||
|
( rostergroups.username,
|
||||||
|
rostergroups.jid,
|
||||||
|
rostergroups.grp
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@JID,
|
||||||
|
@Grp
|
||||||
|
)
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[add_roster_user] ******/
|
||||||
|
/** Add or update user entries in the roster **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[add_roster_user]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250),
|
||||||
|
@Nick varchar(50),
|
||||||
|
@Subscription char(1),
|
||||||
|
@Ask char(1),
|
||||||
|
@AskMessage varchar(250),
|
||||||
|
@Server char(1),
|
||||||
|
@Subscribe varchar(200),
|
||||||
|
@Type varchar(50),
|
||||||
|
@Grp varchar(100) = Null
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
BEGIN TRANSACTION
|
||||||
|
--- Update Roster Users if exist of add new user
|
||||||
|
IF EXISTS (SELECT username FROM rosterusers WHERE rosterusers.username=@Username AND rosterusers.jid=@JID)
|
||||||
|
BEGIN
|
||||||
|
UPDATE rosterusers
|
||||||
|
SET rosterusers.username=@Username,
|
||||||
|
rosterusers.jid=@JID,
|
||||||
|
rosterusers.nick=@Nick,
|
||||||
|
rosterusers.subscription=@Subscription,
|
||||||
|
rosterusers.ask=@Ask,
|
||||||
|
rosterusers.askmessage=@AskMessage,
|
||||||
|
rosterusers.server=@Server,
|
||||||
|
rosterusers.subscribe=@Subscribe,
|
||||||
|
rosterusers.type=@Type
|
||||||
|
WHERE (rosterusers.username=@Username) AND (rosterusers.jid=@JID);
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO rosterusers
|
||||||
|
( rosterusers.username,
|
||||||
|
rosterusers.jid,
|
||||||
|
rosterusers.nick,
|
||||||
|
rosterusers.subscription,
|
||||||
|
rosterusers.ask,
|
||||||
|
rosterusers.askmessage,
|
||||||
|
rosterusers.server,
|
||||||
|
rosterusers.subscribe,
|
||||||
|
rosterusers.type
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@JID,
|
||||||
|
@Nick,
|
||||||
|
@Subscription,
|
||||||
|
@Ask,
|
||||||
|
@AskMessage,
|
||||||
|
@Server,
|
||||||
|
@Subscribe,
|
||||||
|
@Type
|
||||||
|
);
|
||||||
|
END
|
||||||
|
|
||||||
|
--- Update Roster Group if exist of add new group
|
||||||
|
IF @Grp IS NOT NULL
|
||||||
|
EXECUTE [dbo].[add_roster_group] @Username, @JID, @Grp
|
||||||
|
|
||||||
|
COMMIT
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_roster_groups] ******/
|
||||||
|
/** Remove user group entries from the roster groups table **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_roster_groups]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
DELETE FROM rostergroups
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE (rostergroups.username = @Username) AND (rostergroups.jid = @JID);
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[add_spool] ******/
|
||||||
|
/** Add a entry to the spool table **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[add_spool]
|
||||||
|
@Username varchar(250),
|
||||||
|
@XML varchar(8000)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO spool
|
||||||
|
( spool.username,
|
||||||
|
spool.xml
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@XML
|
||||||
|
)
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[add_user] ******/
|
||||||
|
/** Add or update user entries to jabber **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[add_user]
|
||||||
|
@Username varchar(200),
|
||||||
|
@Password varchar(50)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO users
|
||||||
|
( username,
|
||||||
|
[password]
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@Password
|
||||||
|
);
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[set_password] **/
|
||||||
|
/** Update users password **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[set_password]
|
||||||
|
@Username varchar(200),
|
||||||
|
@Password varchar(50)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM users WITH (NOLOCK) WHERE username=@Username)
|
||||||
|
BEGIN
|
||||||
|
UPDATE users SET username=@Username, password=@Password WHERE username=@Username;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO users (username, password) VALUES (@Username, @Password);
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_password] **/
|
||||||
|
/** Retrive the user password **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_password]
|
||||||
|
@Username varchar(200)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
SELECT users.password as password
|
||||||
|
FROM users WITH (NOLOCK)
|
||||||
|
WHERE username=@Username;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[clean_spool_msg] ******/
|
||||||
|
/** Delete messages older that 3 days from spool **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[clean_spool_msg]
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@dt datetime,
|
||||||
|
@myRowCount int
|
||||||
|
BEGIN
|
||||||
|
-- Delete small amounts because if locks the database table
|
||||||
|
SET ROWCOUNT 500
|
||||||
|
SET @myRowCount = 1
|
||||||
|
|
||||||
|
WHILE (@myRowCount) > 0
|
||||||
|
BEGIN
|
||||||
|
BEGIN TRANSACTION
|
||||||
|
SELECT @dt = DATEADD(d, -3, GETDATE())
|
||||||
|
DELETE FROM spool
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE (MustDelete=1) OR (Created < @dt);
|
||||||
|
|
||||||
|
SET @myRowCount = @@RowCount
|
||||||
|
COMMIT
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_last] ******/
|
||||||
|
/** Delete an entry from the last table **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_last]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
DELETE FROM [last]
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE [last].username=@Username;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_roster] ******/
|
||||||
|
/** Delete an entry from the roster **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_roster]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
BEGIN TRANSACTION
|
||||||
|
DELETE FROM rosterusers
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE (rosterusers.username = @Username) AND (rosterusers.jid = @JID);
|
||||||
|
|
||||||
|
DELETE FROM rostergroups
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE (rostergroups.username = @Username) AND (rostergroups.jid = @JID);
|
||||||
|
|
||||||
|
COMMIT
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_spool_msg] ******/
|
||||||
|
/** Delete an entry from the spool table **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_spool_msg]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
DELETE FROM spool
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE spool.username=@Username;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/***************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_user] ******/
|
||||||
|
/** Delete an entry from the user table **/
|
||||||
|
/***************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_user]
|
||||||
|
@Username varchar(200)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
DELETE FROM users
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE username=@Username;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_user_return_password]**/
|
||||||
|
/** Delete an entry from the user table and return user password **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_user_return_password]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@Pwd varchar(50)
|
||||||
|
BEGIN
|
||||||
|
EXECUTE @Pwd = dbo.get_password @Username
|
||||||
|
DELETE FROM users
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE username=@Username
|
||||||
|
|
||||||
|
SELECT @Pwd;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[del_user_roster] **/
|
||||||
|
/** Delete the users roster **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[del_user_roster]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
BEGIN TRANSACTION
|
||||||
|
DELETE FROM rosterusers
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE rosterusers.username = @Username;
|
||||||
|
|
||||||
|
DELETE FROM rostergroups
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE rostergroups.username = @Username;
|
||||||
|
|
||||||
|
COMMIT
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_and_del_spool_msg] **/
|
||||||
|
/** Fetch and delete the users offline messages **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_and_del_spool_msg]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vSpool table( username varchar(1),
|
||||||
|
xml varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM spool with (nolock) WHERE spool.username=@Username)
|
||||||
|
BEGIN
|
||||||
|
SELECT spool.username AS username,
|
||||||
|
spool.xml AS xml
|
||||||
|
FROM spool WITH (NOLOCK)
|
||||||
|
WHERE spool.username=@Username;
|
||||||
|
|
||||||
|
DELETE spool
|
||||||
|
WITH (ROWLOCK)
|
||||||
|
WHERE spool.username=@Username
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vSpool;
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_last] **/
|
||||||
|
/** Retrive the last user login **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_last]
|
||||||
|
@Username varchar(250)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
SELECT last.seconds AS seconds,
|
||||||
|
last.state AS state
|
||||||
|
FROM last WITH (NOLOCK)
|
||||||
|
WHERE last.username=@Username;
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_roster] **/
|
||||||
|
/** Retrive the user roster **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_roster]
|
||||||
|
@Username varchar(200)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vRosterusers table( username varchar(1),
|
||||||
|
jid varchar(1),
|
||||||
|
nick varchar(1),
|
||||||
|
subscription varchar(1),
|
||||||
|
ask varchar(1),
|
||||||
|
askmessage varchar(1),
|
||||||
|
server varchar(1),
|
||||||
|
subscribe varchar(1),
|
||||||
|
type varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rosterusers with (nolock) WHERE rosterusers.username = @Username)
|
||||||
|
BEGIN
|
||||||
|
SELECT rosterusers.username AS username,
|
||||||
|
rosterusers.jid AS jid,
|
||||||
|
rosterusers.nick AS nick,
|
||||||
|
rosterusers.subscription AS subscription,
|
||||||
|
rosterusers.ask AS ask,
|
||||||
|
rosterusers.askmessage AS askmessage,
|
||||||
|
rosterusers.server AS server,
|
||||||
|
rosterusers.subscribe AS subscribe,
|
||||||
|
rosterusers.type AS type
|
||||||
|
FROM rosterusers WITH (NOLOCK)
|
||||||
|
WHERE rosterusers.username = @Username;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vRosterusers
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_roster_by_jid] **/
|
||||||
|
/** Retrive the user roster via JID **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_roster_by_jid]
|
||||||
|
@Username varchar(200),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vRosterusers table( username varchar(1),
|
||||||
|
jid varchar(1),
|
||||||
|
nick varchar(1),
|
||||||
|
subscription varchar(1),
|
||||||
|
ask varchar(1),
|
||||||
|
askmessage varchar(1),
|
||||||
|
server varchar(1),
|
||||||
|
subscribe varchar(1),
|
||||||
|
type varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rosterusers with (nolock) WHERE (rosterusers.username = @Username) AND (rosterusers.jid = @JID))
|
||||||
|
BEGIN
|
||||||
|
SELECT rosterusers.username AS username,
|
||||||
|
rosterusers.jid AS jid,
|
||||||
|
rosterusers.nick AS nick,
|
||||||
|
rosterusers.subscription AS subscription,
|
||||||
|
rosterusers.ask AS ask,
|
||||||
|
rosterusers.askmessage AS askmessage,
|
||||||
|
rosterusers.server AS server,
|
||||||
|
rosterusers.subscribe AS subscribe,
|
||||||
|
rosterusers.type AS type
|
||||||
|
FROM rosterusers WITH (NOLOCK)
|
||||||
|
WHERE (rosterusers.username = @Username) AND (rosterusers.jid = @JID);
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vRosterusers
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_roster_jid_groups] **/
|
||||||
|
/** Retrieve the user roster groups **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_roster_jid_groups]
|
||||||
|
@Username varchar(200)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vrostergroups table( jid varchar(1),
|
||||||
|
grp varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rostergroups with (nolock) WHERE rostergroups.username = @Username)
|
||||||
|
BEGIN
|
||||||
|
SELECT rostergroups.jid AS jid,
|
||||||
|
rostergroups.grp AS grp
|
||||||
|
FROM rostergroups WITH (NOLOCK)
|
||||||
|
WHERE rostergroups.username = @Username;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vrostergroups
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_roster_groups] **/
|
||||||
|
/** Retrive the user roster groups **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_roster_groups]
|
||||||
|
@Username varchar(200),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vrostergroups table( grp varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rostergroups with (nolock) WHERE rostergroups.username = @Username)
|
||||||
|
BEGIN
|
||||||
|
SELECT rostergroups.grp AS grp
|
||||||
|
FROM rostergroups WITH (NOLOCK)
|
||||||
|
WHERE (rostergroups.username = @Username) AND (rostergroups.jid = @JID);
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vrostergroups
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_rostergroup_by_jid] **/
|
||||||
|
/** Retrive the user roster groups via JID **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_rostergroup_by_jid]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vrostergroups table(grp varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rostergroups with (nolock) WHERE rostergroups.username=@Username AND rostergroups.jid=@JID)
|
||||||
|
BEGIN
|
||||||
|
SELECT rostergroups.grp AS grp
|
||||||
|
FROM rostergroups WITH (NOLOCK)
|
||||||
|
WHERE rostergroups.username=@Username AND rostergroups.jid=@JID;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vrostergroups
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[get_subscription] **/
|
||||||
|
/** Retrive the user subscription requests **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[get_subscription]
|
||||||
|
@Username varchar(250),
|
||||||
|
@JID varchar(250)
|
||||||
|
AS
|
||||||
|
DECLARE
|
||||||
|
@vrosterusers table( subscription varchar(1))
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM rosterusers with (nolock) WHERE rosterusers.username=@Username AND rosterusers.jid=@JID)
|
||||||
|
BEGIN
|
||||||
|
SELECT rosterusers.subscription AS subscription
|
||||||
|
FROM rosterusers WITH (NOLOCK)
|
||||||
|
WHERE rosterusers.username=@Username AND rosterusers.jid=@JID;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
SELECT * FROM @vrosterusers
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[list_users] **/
|
||||||
|
/** Retrive a list of all users **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[list_users]
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
SELECT users.username AS username FROM users WITH (NOLOCK);
|
||||||
|
END
|
||||||
|
GO
|
||||||
|
|
||||||
|
/******************************************************************/
|
||||||
|
/****** Object: StoredProcedure [dbo].[set_last] **/
|
||||||
|
/** Update users last login status **/
|
||||||
|
/******************************************************************/
|
||||||
|
CREATE PROCEDURE [dbo].[set_last]
|
||||||
|
@Username varchar(250),
|
||||||
|
@Seconds varchar(50),
|
||||||
|
@State varchar(100)
|
||||||
|
AS
|
||||||
|
BEGIN
|
||||||
|
IF EXISTS (SELECT username FROM [last] WITH (NOLOCK) WHERE username=@Username)
|
||||||
|
BEGIN
|
||||||
|
UPDATE [last]
|
||||||
|
SET [last].username = @Username,
|
||||||
|
[last].seconds = @Seconds,
|
||||||
|
[last].state = @State
|
||||||
|
WHERE last.username=@Username;
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
BEGIN
|
||||||
|
INSERT INTO [last]
|
||||||
|
( [last].username,
|
||||||
|
[last].seconds,
|
||||||
|
[last].state
|
||||||
|
)
|
||||||
|
VALUES
|
||||||
|
( @Username,
|
||||||
|
@Seconds,
|
||||||
|
@State
|
||||||
|
)
|
||||||
|
END
|
||||||
|
END
|
||||||
|
GO
|
434
src/odbc/odbc_queries.erl
Normal file
434
src/odbc/odbc_queries.erl
Normal file
|
@ -0,0 +1,434 @@
|
||||||
|
%% Copyrigh 2006, Process-one
|
||||||
|
%% This module is intended to take into account relational databases behaviour
|
||||||
|
%% differences
|
||||||
|
-module(odbc_queries).
|
||||||
|
-author("mickael.remond@process-one.net").
|
||||||
|
|
||||||
|
-export([get_db_type/0,
|
||||||
|
sql_transaction/2,
|
||||||
|
get_last/2,
|
||||||
|
set_last_t/4,
|
||||||
|
del_last/2,
|
||||||
|
get_password/2,
|
||||||
|
set_password_t/3,
|
||||||
|
add_user/3,
|
||||||
|
del_user/2,
|
||||||
|
del_user_return_password/3,
|
||||||
|
list_users/1,
|
||||||
|
add_spool_sql/2,
|
||||||
|
add_spool/2,
|
||||||
|
get_and_del_spool_msg_t/2,
|
||||||
|
del_spool_msg/2,
|
||||||
|
get_roster/2,
|
||||||
|
get_roster_jid_groups/2,
|
||||||
|
get_roster_groups/3,
|
||||||
|
del_user_roster_t/2,
|
||||||
|
get_roster_by_jid/3,
|
||||||
|
get_rostergroup_by_jid/3,
|
||||||
|
del_roster/3,
|
||||||
|
del_roster_sql/2,
|
||||||
|
update_roster/5,
|
||||||
|
update_roster_sql/4,
|
||||||
|
roster_subscribe/4,
|
||||||
|
get_subscription/3,
|
||||||
|
escape/1]).
|
||||||
|
|
||||||
|
%-define(generic, true).
|
||||||
|
%-define(mssql, true).
|
||||||
|
|
||||||
|
%% -----------------
|
||||||
|
%% Generic queries
|
||||||
|
-ifdef(generic).
|
||||||
|
|
||||||
|
get_db_type() ->
|
||||||
|
generic.
|
||||||
|
|
||||||
|
sql_transaction(LServer, F) ->
|
||||||
|
ejabberd_odbc:sql_transaction(LServer, F).
|
||||||
|
|
||||||
|
get_last(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select seconds, state from last "
|
||||||
|
"where username='", Username, "'"]).
|
||||||
|
|
||||||
|
set_last_t(LServer, Username, Seconds, State) ->
|
||||||
|
%% MREMOND: I think this should be turn into a non transactional behaviour
|
||||||
|
ejabberd_odbc:sql_transaction(
|
||||||
|
LServer,
|
||||||
|
[["delete from last where username='", Username, "';"],
|
||||||
|
["insert into last(username, seconds, state) "
|
||||||
|
"values ('", Username, "', '", Seconds, "', '", State, "');"]]).
|
||||||
|
|
||||||
|
del_last(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["delete from last where username='", Username, "'"]).
|
||||||
|
|
||||||
|
get_password(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select password from users "
|
||||||
|
"where username='", Username, "';"]).
|
||||||
|
|
||||||
|
set_password_t(LServer, Username, Pass) ->
|
||||||
|
ejabberd_odbc:sql_transaction(
|
||||||
|
LServer,
|
||||||
|
[["delete from users where username='", Username ,"';"],
|
||||||
|
["insert into users(username, password) "
|
||||||
|
"values ('", Username, "', '", Pass, "');"]]).
|
||||||
|
|
||||||
|
add_user(LServer, Username, Pass) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["insert into users(username, password) "
|
||||||
|
"values ('", Username, "', '", Pass, "');"]).
|
||||||
|
|
||||||
|
del_user(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["delete from users where username='", Username ,"';"]).
|
||||||
|
|
||||||
|
del_user_return_password(_LServer, Username, Pass) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["select password from users where username='",
|
||||||
|
Username, "';"]),
|
||||||
|
ejabberd_odbc:sql_query_t(["delete from users "
|
||||||
|
"where username='", Username,
|
||||||
|
"' and password='", Pass, "';"]).
|
||||||
|
|
||||||
|
list_users(LServer) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
"select username from users").
|
||||||
|
|
||||||
|
add_spool_sql(Username, XML) ->
|
||||||
|
["insert into spool(username, xml) "
|
||||||
|
"values ('", Username, "', '",
|
||||||
|
XML,
|
||||||
|
"');"].
|
||||||
|
|
||||||
|
add_spool(LServer, Queries) ->
|
||||||
|
ejabberd_odbc:sql_transaction(
|
||||||
|
LServer, Queries).
|
||||||
|
|
||||||
|
get_and_del_spool_msg_t(LServer, Username) ->
|
||||||
|
F = fun() ->
|
||||||
|
Result = ejabberd_odbc:sql_query_t(
|
||||||
|
["select username, xml from spool where username='", Username, "'"
|
||||||
|
" order by seq;"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from spool where username='", Username, "';"]),
|
||||||
|
Result
|
||||||
|
end,
|
||||||
|
ejabberd_odbc:sql_transaction(LServer,F).
|
||||||
|
|
||||||
|
del_spool_msg(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["delete from spool where username='", Username, "';"]).
|
||||||
|
|
||||||
|
get_roster(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select username, jid, nick, subscription, ask, "
|
||||||
|
"askmessage, server, subscribe, type from rosterusers "
|
||||||
|
"where username='", Username, "'"]).
|
||||||
|
|
||||||
|
get_roster_jid_groups(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select jid, grp from rostergroups "
|
||||||
|
"where username='", Username, "'"]).
|
||||||
|
|
||||||
|
get_roster_groups(_LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["select grp from rostergroups "
|
||||||
|
"where username='", Username, "' "
|
||||||
|
"and jid='", SJID, "';"]).
|
||||||
|
|
||||||
|
del_user_roster_t(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_transaction(
|
||||||
|
LServer,
|
||||||
|
fun() ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rosterusers "
|
||||||
|
" where username='", Username, "';"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rostergroups "
|
||||||
|
" where username='", Username, "';"])
|
||||||
|
end).
|
||||||
|
|
||||||
|
get_roster_by_jid(_LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["select username, jid, nick, subscription, "
|
||||||
|
"ask, askmessage, server, subscribe, type from rosterusers "
|
||||||
|
"where username='", Username, "' "
|
||||||
|
"and jid='", SJID, "';"]).
|
||||||
|
|
||||||
|
get_rostergroup_by_jid(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select grp from rostergroups "
|
||||||
|
"where username='", Username, "' "
|
||||||
|
"and jid='", SJID, "'"]).
|
||||||
|
|
||||||
|
del_roster(_LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rosterusers "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rostergroups "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]).
|
||||||
|
|
||||||
|
del_roster_sql(Username, SJID) ->
|
||||||
|
[["delete from rosterusers "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"],
|
||||||
|
["delete from rostergroups "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]].
|
||||||
|
|
||||||
|
update_roster(_LServer, Username, SJID, ItemVals, ItemGroups) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rosterusers "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["insert into rosterusers("
|
||||||
|
" username, jid, nick, "
|
||||||
|
" subscription, ask, askmessage, "
|
||||||
|
" server, subscribe, type) "
|
||||||
|
" values (", ItemVals, ");"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rostergroups "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]),
|
||||||
|
lists:foreach(fun(ItemGroup) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["insert into rostergroups("
|
||||||
|
" username, jid, grp) "
|
||||||
|
" values (", ItemGroup, ");"])
|
||||||
|
end,
|
||||||
|
ItemGroups).
|
||||||
|
|
||||||
|
update_roster_sql(Username, SJID, ItemVals, ItemGroups) ->
|
||||||
|
[["delete from rosterusers "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"],
|
||||||
|
["insert into rosterusers("
|
||||||
|
" username, jid, nick, "
|
||||||
|
" subscription, ask, askmessage"
|
||||||
|
" server, subscribe, type) "
|
||||||
|
" values (", ItemVals, ");"],
|
||||||
|
["delete from rostergroups "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"],
|
||||||
|
[["insert into rostergroups("
|
||||||
|
" username, jid, grp) "
|
||||||
|
" values (", ItemGroup, ");"] ||
|
||||||
|
ItemGroup <- ItemGroups]].
|
||||||
|
|
||||||
|
roster_subscribe(_LServer, Username, SJID, ItemVals) ->
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["delete from rosterusers "
|
||||||
|
" where username='", Username, "' "
|
||||||
|
" and jid='", SJID, "';"]),
|
||||||
|
ejabberd_odbc:sql_query_t(
|
||||||
|
["insert into rosterusers("
|
||||||
|
" username, jid, nick, "
|
||||||
|
" subscription, ask, askmessage, "
|
||||||
|
" server, subscribe, type) "
|
||||||
|
" values (", ItemVals, ");"]).
|
||||||
|
|
||||||
|
get_subscription(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["select subscription from rosterusers "
|
||||||
|
"where username='", Username, "' "
|
||||||
|
"and jid='", SJID, "'"]).
|
||||||
|
|
||||||
|
%% Characters to escape
|
||||||
|
escape($\0) -> "\\0";
|
||||||
|
escape($\n) -> "\\n";
|
||||||
|
escape($\t) -> "\\t";
|
||||||
|
escape($\b) -> "\\b";
|
||||||
|
escape($\r) -> "\\r";
|
||||||
|
escape($') -> "\\'";
|
||||||
|
escape($") -> "\\\"";
|
||||||
|
escape($\\) -> "\\\\";
|
||||||
|
escape(C) -> C.
|
||||||
|
|
||||||
|
-endif.
|
||||||
|
|
||||||
|
%% -----------------
|
||||||
|
%% MSSQL queries
|
||||||
|
-ifdef(mssql).
|
||||||
|
|
||||||
|
get_db_type() ->
|
||||||
|
mssql.
|
||||||
|
|
||||||
|
sql_transaction(_LServer, F) ->
|
||||||
|
{atomic, catch F()}.
|
||||||
|
|
||||||
|
get_last(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_last '", Username, "'"]).
|
||||||
|
|
||||||
|
set_last_t(LServer, Username, Seconds, State) ->
|
||||||
|
Result = ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.set_last '", Username, "', '", Seconds,
|
||||||
|
"', '", State, "'"]),
|
||||||
|
{atomic, Result}.
|
||||||
|
|
||||||
|
del_last(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_last '", Username, "'"]).
|
||||||
|
|
||||||
|
get_password(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_password '", Username, "'"]).
|
||||||
|
|
||||||
|
set_password_t(LServer, Username, Pass) ->
|
||||||
|
Result = ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.set_password '", Username, "', '", Pass, "'"]),
|
||||||
|
{atomic, Result}.
|
||||||
|
|
||||||
|
add_user(LServer, Username, Pass) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.add_user '", Username, "', '", Pass, "'"]).
|
||||||
|
|
||||||
|
del_user(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_user '", Username ,"'"]).
|
||||||
|
|
||||||
|
del_user_return_password(LServer, Username, Pass) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_user_return_password '", Username, "'"]),
|
||||||
|
Pass.
|
||||||
|
|
||||||
|
list_users(LServer) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
"EXECUTE dbo.list_users").
|
||||||
|
|
||||||
|
add_spool_sql(Username, XML) ->
|
||||||
|
["EXECUTE dbo.add_spool '", Username, "' , '",XML,"'"].
|
||||||
|
|
||||||
|
add_spool(LServer, Queries) ->
|
||||||
|
lists:foreach(fun(Query) ->
|
||||||
|
ejabberd_odbc:sql_query(LServer, Query)
|
||||||
|
end,
|
||||||
|
Queries).
|
||||||
|
|
||||||
|
get_and_del_spool_msg_t(LServer, Username) ->
|
||||||
|
[Result] = case ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_and_del_spool_msg '", Username, "'"]) of
|
||||||
|
Rs when list(Rs) ->
|
||||||
|
lists:filter(fun({selected, _Header, _Row}) ->
|
||||||
|
true;
|
||||||
|
({updated, _N}) ->
|
||||||
|
false
|
||||||
|
end,
|
||||||
|
Rs);
|
||||||
|
Rs -> [Rs]
|
||||||
|
end,
|
||||||
|
{atomic, Result}.
|
||||||
|
|
||||||
|
del_spool_msg(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_spool_msg '", Username, "'"]).
|
||||||
|
|
||||||
|
get_roster(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_roster '", Username, "'"]).
|
||||||
|
|
||||||
|
get_roster_jid_groups(LServer, Username) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_roster_jid_groups '", Username, "'"]).
|
||||||
|
|
||||||
|
get_roster_groups(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_roster_groups '", Username, "' , '", SJID, "'"]).
|
||||||
|
|
||||||
|
del_user_roster_t(LServer, Username) ->
|
||||||
|
Result = ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_user_roster '", Username, "'"]),
|
||||||
|
{atomic, Result}.
|
||||||
|
|
||||||
|
get_roster_by_jid(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_roster_by_jid '", Username, "' , '", SJID, "'"]).
|
||||||
|
|
||||||
|
get_rostergroup_by_jid(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_rostergroup_by_jid '", Username, "' , '", SJID, "'"]).
|
||||||
|
|
||||||
|
del_roster(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.del_roster '", Username, "', '", SJID, "'"]).
|
||||||
|
|
||||||
|
del_roster_sql(Username, SJID) ->
|
||||||
|
["EXECUTE dbo.del_roster '", Username, "', '", SJID, "'"].
|
||||||
|
|
||||||
|
update_roster(LServer, Username, SJID, ItemVals, ItemGroups) ->
|
||||||
|
Query1 = ["EXECUTE dbo.del_roster '", Username, "', '", SJID, "' "],
|
||||||
|
ejabberd_odbc:sql_query(LServer, lists:flatten(Query1)),
|
||||||
|
Query2 = ["EXECUTE dbo.add_roster_user ", ItemVals],
|
||||||
|
ejabberd_odbc:sql_query(LServer, lists:flatten(Query2)),
|
||||||
|
Query3 = ["EXECUTE dbo.del_roster_groups '", Username, "', '", SJID, "' "],
|
||||||
|
ejabberd_odbc:sql_query(LServer, lists:flatten(Query3)),
|
||||||
|
lists:foreach(fun(ItemGroup) ->
|
||||||
|
Query = ["EXECUTE dbo.add_roster_group ",
|
||||||
|
ItemGroup],
|
||||||
|
ejabberd_odbc:sql_query(LServer,
|
||||||
|
lists:flatten(Query))
|
||||||
|
end,
|
||||||
|
ItemGroups).
|
||||||
|
|
||||||
|
update_roster_sql(Username, SJID, ItemVals, ItemGroups) ->
|
||||||
|
["BEGIN TRANSACTION ",
|
||||||
|
"EXECUTE dbo.del_roster_groups '", Username, "','", SJID, "' ",
|
||||||
|
"EXECUTE dbo.add_roster_user ", ItemVals, " "] ++
|
||||||
|
[lists:flatten("EXECUTE dbo.add_roster_group ", ItemGroup, " ")
|
||||||
|
|| ItemGroup <- ItemGroups] ++
|
||||||
|
["COMMIT"].
|
||||||
|
|
||||||
|
roster_subscribe(LServer, _Username, _SJID, ItemVals) ->
|
||||||
|
catch ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.add_roster_user ", ItemVals]).
|
||||||
|
|
||||||
|
get_subscription(LServer, Username, SJID) ->
|
||||||
|
ejabberd_odbc:sql_query(
|
||||||
|
LServer,
|
||||||
|
["EXECUTE dbo.get_subscription '", Username, "' , '", SJID, "'"]).
|
||||||
|
|
||||||
|
%% Characters to escape
|
||||||
|
escape($\0) -> "\\0";
|
||||||
|
escape($\t) -> "\\t";
|
||||||
|
escape($\b) -> "\\b";
|
||||||
|
escape($\r) -> "\\r";
|
||||||
|
escape($') -> "\''";
|
||||||
|
escape($") -> "\\\"";
|
||||||
|
escape(C) -> C.
|
||||||
|
-endif.
|
|
@ -18,7 +18,7 @@ CREATE TABLE rosterusers (
|
||||||
nick text,
|
nick text,
|
||||||
subscription character(1) NOT NULL,
|
subscription character(1) NOT NULL,
|
||||||
ask character(1) NOT NULL,
|
ask character(1) NOT NULL,
|
||||||
askmessage text NOT NULL,
|
askmessage text,
|
||||||
server character(1) NOT NULL,
|
server character(1) NOT NULL,
|
||||||
subscribe text,
|
subscribe text,
|
||||||
"type" text
|
"type" text
|
||||||
|
|
Loading…
Reference in New Issue
Block a user