Browse code

Initial import of the new module purple

git-svn-id: https://openser.svn.sourceforge.net/svnroot/openser/trunk@5525 689a6050-402a-0410-94f2-e92a70836424

Eric Ptak authored on 28/01/2009 16:48:22
Showing 39 changed files
... ...
@@ -52,6 +52,7 @@
52 52
 #define MI_SUBSCRIBE        1<<8
53 53
 #define RLS_SUBSCRIBE       1<<9
54 54
 #define DIALOG_PUBLISH      1<<10
55
+#define PURPLE_PUBLISH      1<<11
55 56
 
56 57
 #define NO_UPDATEDB_FLAG    1<<0
57 58
 #define UPDATEDB_FLAG       1<<1
58 59
new file mode 100644
... ...
@@ -0,0 +1,340 @@
0
+		    GNU GENERAL PUBLIC LICENSE
1
+		       Version 2, June 1991
2
+
3
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
4
+ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
5
+ Everyone is permitted to copy and distribute verbatim copies
6
+ of this license document, but changing it is not allowed.
7
+
8
+			    Preamble
9
+
10
+  The licenses for most software are designed to take away your
11
+freedom to share and change it.  By contrast, the GNU General Public
12
+License is intended to guarantee your freedom to share and change free
13
+software--to make sure the software is free for all its users.  This
14
+General Public License applies to most of the Free Software
15
+Foundation's software and to any other program whose authors commit to
16
+using it.  (Some other Free Software Foundation software is covered by
17
+the GNU Lesser General Public License instead.)  You can apply it to
18
+your programs, too.
19
+
20
+  When we speak of free software, we are referring to freedom, not
21
+price.  Our General Public Licenses are designed to make sure that you
22
+have the freedom to distribute copies of free software (and charge for
23
+this service if you wish), that you receive source code or can get it
24
+if you want it, that you can change the software or use pieces of it
25
+in new free programs; and that you know you can do these things.
26
+
27
+  To protect your rights, we need to make restrictions that forbid
28
+anyone to deny you these rights or to ask you to surrender the rights.
29
+These restrictions translate to certain responsibilities for you if you
30
+distribute copies of the software, or if you modify it.
31
+
32
+  For example, if you distribute copies of such a program, whether
33
+gratis or for a fee, you must give the recipients all the rights that
34
+you have.  You must make sure that they, too, receive or can get the
35
+source code.  And you must show them these terms so they know their
36
+rights.
37
+
38
+  We protect your rights with two steps: (1) copyright the software, and
39
+(2) offer you this license which gives you legal permission to copy,
40
+distribute and/or modify the software.
41
+
42
+  Also, for each author's protection and ours, we want to make certain
43
+that everyone understands that there is no warranty for this free
44
+software.  If the software is modified by someone else and passed on, we
45
+want its recipients to know that what they have is not the original, so
46
+that any problems introduced by others will not reflect on the original
47
+authors' reputations.
48
+
49
+  Finally, any free program is threatened constantly by software
50
+patents.  We wish to avoid the danger that redistributors of a free
51
+program will individually obtain patent licenses, in effect making the
52
+program proprietary.  To prevent this, we have made it clear that any
53
+patent must be licensed for everyone's free use or not licensed at all.
54
+
55
+  The precise terms and conditions for copying, distribution and
56
+modification follow.
57
+
58
+		    GNU GENERAL PUBLIC LICENSE
59
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
60
+
61
+  0. This License applies to any program or other work which contains
62
+a notice placed by the copyright holder saying it may be distributed
63
+under the terms of this General Public License.  The "Program", below,
64
+refers to any such program or work, and a "work based on the Program"
65
+means either the Program or any derivative work under copyright law:
66
+that is to say, a work containing the Program or a portion of it,
67
+either verbatim or with modifications and/or translated into another
68
+language.  (Hereinafter, translation is included without limitation in
69
+the term "modification".)  Each licensee is addressed as "you".
70
+
71
+Activities other than copying, distribution and modification are not
72
+covered by this License; they are outside its scope.  The act of
73
+running the Program is not restricted, and the output from the Program
74
+is covered only if its contents constitute a work based on the
75
+Program (independent of having been made by running the Program).
76
+Whether that is true depends on what the Program does.
77
+
78
+  1. You may copy and distribute verbatim copies of the Program's
79
+source code as you receive it, in any medium, provided that you
80
+conspicuously and appropriately publish on each copy an appropriate
81
+copyright notice and disclaimer of warranty; keep intact all the
82
+notices that refer to this License and to the absence of any warranty;
83
+and give any other recipients of the Program a copy of this License
84
+along with the Program.
85
+
86
+You may charge a fee for the physical act of transferring a copy, and
87
+you may at your option offer warranty protection in exchange for a fee.
88
+
89
+  2. You may modify your copy or copies of the Program or any portion
90
+of it, thus forming a work based on the Program, and copy and
91
+distribute such modifications or work under the terms of Section 1
92
+above, provided that you also meet all of these conditions:
93
+
94
+    a) You must cause the modified files to carry prominent notices
95
+    stating that you changed the files and the date of any change.
96
+
97
+    b) You must cause any work that you distribute or publish, that in
98
+    whole or in part contains or is derived from the Program or any
99
+    part thereof, to be licensed as a whole at no charge to all third
100
+    parties under the terms of this License.
101
+
102
+    c) If the modified program normally reads commands interactively
103
+    when run, you must cause it, when started running for such
104
+    interactive use in the most ordinary way, to print or display an
105
+    announcement including an appropriate copyright notice and a
106
+    notice that there is no warranty (or else, saying that you provide
107
+    a warranty) and that users may redistribute the program under
108
+    these conditions, and telling the user how to view a copy of this
109
+    License.  (Exception: if the Program itself is interactive but
110
+    does not normally print such an announcement, your work based on
111
+    the Program is not required to print an announcement.)
112
+
113
+These requirements apply to the modified work as a whole.  If
114
+identifiable sections of that work are not derived from the Program,
115
+and can be reasonably considered independent and separate works in
116
+themselves, then this License, and its terms, do not apply to those
117
+sections when you distribute them as separate works.  But when you
118
+distribute the same sections as part of a whole which is a work based
119
+on the Program, the distribution of the whole must be on the terms of
120
+this License, whose permissions for other licensees extend to the
121
+entire whole, and thus to each and every part regardless of who wrote it.
122
+
123
+Thus, it is not the intent of this section to claim rights or contest
124
+your rights to work written entirely by you; rather, the intent is to
125
+exercise the right to control the distribution of derivative or
126
+collective works based on the Program.
127
+
128
+In addition, mere aggregation of another work not based on the Program
129
+with the Program (or with a work based on the Program) on a volume of
130
+a storage or distribution medium does not bring the other work under
131
+the scope of this License.
132
+
133
+  3. You may copy and distribute the Program (or a work based on it,
134
+under Section 2) in object code or executable form under the terms of
135
+Sections 1 and 2 above provided that you also do one of the following:
136
+
137
+    a) Accompany it with the complete corresponding machine-readable
138
+    source code, which must be distributed under the terms of Sections
139
+    1 and 2 above on a medium customarily used for software interchange; or,
140
+
141
+    b) Accompany it with a written offer, valid for at least three
142
+    years, to give any third party, for a charge no more than your
143
+    cost of physically performing source distribution, a complete
144
+    machine-readable copy of the corresponding source code, to be
145
+    distributed under the terms of Sections 1 and 2 above on a medium
146
+    customarily used for software interchange; or,
147
+
148
+    c) Accompany it with the information you received as to the offer
149
+    to distribute corresponding source code.  (This alternative is
150
+    allowed only for noncommercial distribution and only if you
151
+    received the program in object code or executable form with such
152
+    an offer, in accord with Subsection b above.)
153
+
154
+The source code for a work means the preferred form of the work for
155
+making modifications to it.  For an executable work, complete source
156
+code means all the source code for all modules it contains, plus any
157
+associated interface definition files, plus the scripts used to
158
+control compilation and installation of the executable.  However, as a
159
+special exception, the source code distributed need not include
160
+anything that is normally distributed (in either source or binary
161
+form) with the major components (compiler, kernel, and so on) of the
162
+operating system on which the executable runs, unless that component
163
+itself accompanies the executable.
164
+
165
+If distribution of executable or object code is made by offering
166
+access to copy from a designated place, then offering equivalent
167
+access to copy the source code from the same place counts as
168
+distribution of the source code, even though third parties are not
169
+compelled to copy the source along with the object code.
170
+
171
+  4. You may not copy, modify, sublicense, or distribute the Program
172
+except as expressly provided under this License.  Any attempt
173
+otherwise to copy, modify, sublicense or distribute the Program is
174
+void, and will automatically terminate your rights under this License.
175
+However, parties who have received copies, or rights, from you under
176
+this License will not have their licenses terminated so long as such
177
+parties remain in full compliance.
178
+
179
+  5. You are not required to accept this License, since you have not
180
+signed it.  However, nothing else grants you permission to modify or
181
+distribute the Program or its derivative works.  These actions are
182
+prohibited by law if you do not accept this License.  Therefore, by
183
+modifying or distributing the Program (or any work based on the
184
+Program), you indicate your acceptance of this License to do so, and
185
+all its terms and conditions for copying, distributing or modifying
186
+the Program or works based on it.
187
+
188
+  6. Each time you redistribute the Program (or any work based on the
189
+Program), the recipient automatically receives a license from the
190
+original licensor to copy, distribute or modify the Program subject to
191
+these terms and conditions.  You may not impose any further
192
+restrictions on the recipients' exercise of the rights granted herein.
193
+You are not responsible for enforcing compliance by third parties to
194
+this License.
195
+
196
+  7. If, as a consequence of a court judgment or allegation of patent
197
+infringement or for any other reason (not limited to patent issues),
198
+conditions are imposed on you (whether by court order, agreement or
199
+otherwise) that contradict the conditions of this License, they do not
200
+excuse you from the conditions of this License.  If you cannot
201
+distribute so as to satisfy simultaneously your obligations under this
202
+License and any other pertinent obligations, then as a consequence you
203
+may not distribute the Program at all.  For example, if a patent
204
+license would not permit royalty-free redistribution of the Program by
205
+all those who receive copies directly or indirectly through you, then
206
+the only way you could satisfy both it and this License would be to
207
+refrain entirely from distribution of the Program.
208
+
209
+If any portion of this section is held invalid or unenforceable under
210
+any particular circumstance, the balance of the section is intended to
211
+apply and the section as a whole is intended to apply in other
212
+circumstances.
213
+
214
+It is not the purpose of this section to induce you to infringe any
215
+patents or other property right claims or to contest validity of any
216
+such claims; this section has the sole purpose of protecting the
217
+integrity of the free software distribution system, which is
218
+implemented by public license practices.  Many people have made
219
+generous contributions to the wide range of software distributed
220
+through that system in reliance on consistent application of that
221
+system; it is up to the author/donor to decide if he or she is willing
222
+to distribute software through any other system and a licensee cannot
223
+impose that choice.
224
+
225
+This section is intended to make thoroughly clear what is believed to
226
+be a consequence of the rest of this License.
227
+
228
+  8. If the distribution and/or use of the Program is restricted in
229
+certain countries either by patents or by copyrighted interfaces, the
230
+original copyright holder who places the Program under this License
231
+may add an explicit geographical distribution limitation excluding
232
+those countries, so that distribution is permitted only in or among
233
+countries not thus excluded.  In such case, this License incorporates
234
+the limitation as if written in the body of this License.
235
+
236
+  9. The Free Software Foundation may publish revised and/or new versions
237
+of the General Public License from time to time.  Such new versions will
238
+be similar in spirit to the present version, but may differ in detail to
239
+address new problems or concerns.
240
+
241
+Each version is given a distinguishing version number.  If the Program
242
+specifies a version number of this License which applies to it and "any
243
+later version", you have the option of following the terms and conditions
244
+either of that version or of any later version published by the Free
245
+Software Foundation.  If the Program does not specify a version number of
246
+this License, you may choose any version ever published by the Free Software
247
+Foundation.
248
+
249
+  10. If you wish to incorporate parts of the Program into other free
250
+programs whose distribution conditions are different, write to the author
251
+to ask for permission.  For software which is copyrighted by the Free
252
+Software Foundation, write to the Free Software Foundation; we sometimes
253
+make exceptions for this.  Our decision will be guided by the two goals
254
+of preserving the free status of all derivatives of our free software and
255
+of promoting the sharing and reuse of software generally.
256
+
257
+			    NO WARRANTY
258
+
259
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
260
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
261
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
262
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
263
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
264
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
265
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
266
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
267
+REPAIR OR CORRECTION.
268
+
269
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
270
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
271
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
272
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
273
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
274
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
275
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
276
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
277
+POSSIBILITY OF SUCH DAMAGES.
278
+
279
+		     END OF TERMS AND CONDITIONS
280
+
281
+	    How to Apply These Terms to Your New Programs
282
+
283
+  If you develop a new program, and you want it to be of the greatest
284
+possible use to the public, the best way to achieve this is to make it
285
+free software which everyone can redistribute and change under these terms.
286
+
287
+  To do so, attach the following notices to the program.  It is safest
288
+to attach them to the start of each source file to most effectively
289
+convey the exclusion of warranty; and each file should have at least
290
+the "copyright" line and a pointer to where the full notice is found.
291
+
292
+    <one line to give the program's name and a brief idea of what it does.>
293
+    Copyright (C) <year>  <name of author>
294
+
295
+    This program is free software; you can redistribute it and/or modify
296
+    it under the terms of the GNU General Public License as published by
297
+    the Free Software Foundation; either version 2 of the License, or
298
+    (at your option) any later version.
299
+
300
+    This program is distributed in the hope that it will be useful,
301
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
302
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
303
+    GNU General Public License for more details.
304
+
305
+    You should have received a copy of the GNU General Public License along
306
+    with this program; if not, write to the Free Software Foundation, Inc.,
307
+    51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
308
+
309
+Also add information on how to contact you by electronic and paper mail.
310
+
311
+If the program is interactive, make it output a short notice like this
312
+when it starts in an interactive mode:
313
+
314
+    Gnomovision version 69, Copyright (C) year name of author
315
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
316
+    This is free software, and you are welcome to redistribute it
317
+    under certain conditions; type `show c' for details.
318
+
319
+The hypothetical commands `show w' and `show c' should show the appropriate
320
+parts of the General Public License.  Of course, the commands you use may
321
+be called something other than `show w' and `show c'; they could even be
322
+mouse-clicks or menu items--whatever suits your program.
323
+
324
+You should also get your employer (if you work as a programmer) or your
325
+school, if any, to sign a "copyright disclaimer" for the program, if
326
+necessary.  Here is a sample; alter the names:
327
+
328
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
329
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
330
+
331
+  <signature of Ty Coon>, 1 April 1989
332
+  Ty Coon, President of Vice
333
+
334
+This General Public License does not permit incorporating your program into
335
+proprietary programs.  If your program is a subroutine library, you may
336
+consider it more useful to permit linking proprietary applications with the
337
+library.  If this is what you want to do, use the GNU Lesser General
338
+Public License instead of this License.
339
+
0 340
new file mode 100644
... ...
@@ -0,0 +1,11 @@
0
+include ../../Makefile.defs
1
+auto_gen=
2
+NAME=purple.so
3
+LIBS= 
4
+
5
+DEFS+=-I/usr/lib/glib-2.0/include -I/usr/include/glib-2.0 \
6
+		-I/usr/include/libxml2
7
+LIBS+=-lglib-2.0 -lpurple -lxml2
8
+
9
+
10
+include ../../Makefile.modules
0 11
new file mode 100644
... ...
@@ -0,0 +1,165 @@
0
+OpenSER PURPLE MODULE
1
+---------------------
2
+
3
+Copyright (C) 2008 Atos Worldline
4
+Contact: Eric PTAK <eric.ptak@atosorigin.com>
5
+
6
+This program is free software: you can redistribute it and/or modify
7
+it under the terms of the GNU General Public License as published by
8
+the Free Software Foundation, either version 2 of the License, or
9
+(at your option) any later version.
10
+
11
+This program is distributed in the hope that it will be useful,
12
+but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
+GNU General Public License for more details.
15
+
16
+You should have received a copy of the GNU General Public License
17
+along with this program.  If not, see <http://www.gnu.org/licenses/>.
18
+
19
+
20
+Introduction
21
+------------
22
+Purple module is a multi-protocol instant-messaging gateway module which use libpurple, the library on bottom of Pidgin (ex-gaim).
23
+This plugin was wrote in order to proof the concept of gateway between SIP and MSN/Live networks. As libpurple is written to code multi-protocol 
24
+graphic IM clients , it provides a high level API in order to manipulate accounts, contacts, contacts lists, conversations and more. So this module 
25
+provides a multi-protocol IM/Presence client running inside OpenSER with an account for each protocols used by each SIP user whereas libpurple is 
26
+designed for a graphic client for only one user. So it's no really adapted to a production environment with a huge user count but can be used in order 
27
+to demonstrate the concept or to use it in SOHO environment.
28
+
29
+Requirements
30
+------------
31
+* OpenSER fork 1.5.x devel trunk (eg. Kamailio/OpenSIPS)
32
+* modules : presence*, pua, db_?
33
+* database
34
+* libpurple from pidgin 2.5.2
35
+
36
+PUA mod
37
+-------
38
+In order to compile the module, you'll need to add a PURPLE_PUBLISH preprocessor definition to modules/pua/hash.h after others *_PUBLISH.
39
+* Kamailio :
40
+[...]
41
+#define RLS_SUBSCRIBE       1<<9
42
+#define DIALOG_PUBLISH      1<<10
43
+#define PURPLE_PUBLISH      1<<11
44
+
45
+* OpenSIPS :
46
+[...]
47
+#define MI_SUBSCRIBE        1<<8
48
+#define RLS_SUBSCRIBE       1<<9
49
+#define PURPLE_PUBLISH      1<<10
50
+
51
+
52
+openserctl mod
53
+--------------
54
+By default - and I don't know exactly why - there's some undefined symbol errors with libpurple shared object when using inside OpenSER.
55
+To solve it, you have to force preload of the library by setting up LD_PRELOAD environment variable.
56
+So you should add to your [openser|kam|opensips]ctl (adapt the path to your environment) :
57
+export LD_PRELOAD=$LD_PRELOAD:/usr/local/lib/libpurple.so
58
+
59
+
60
+Database scheme
61
+---------------
62
+The database is used to map SIP URIs with external accounts (eg. MSN)
63
+
64
+	+----------+------------------+------+-----+---------+----------------+
65
+	| Field    | Type             | Null | Key | Default | Extra          |
66
+	+----------+------------------+------+-----+---------+----------------+
67
+	| id       | int(10) unsigned | NO   | PRI | NULL    | auto_increment |
68
+	| sip_user | varchar(128)     | NO   |     | NULL    |                |
69
+	| ext_user | varchar(128)     | NO   |     | NULL    |                |
70
+	| ext_prot | varchar(16)      | NO   |     | NULL    |                |
71
+	| ext_pass | varchar(64)      | YES  |     | NULL    |                |
72
+	+----------+------------------+------+-----+---------+----------------+
73
+
74
+Details :
75
+	* sip_user : user's SIP URI
76
+	* ext_user : user's external account login
77
+	* ext_prot : purple plugin id to use, except for gtalk
78
+	* ext_pass : user's external account password
79
+
80
+Example :
81
+	+----+------------------+-----------------+----------------+----------+
82
+	| id | sip_user         | ext_user        | ext_prot       | ext_pass |
83
+	+----+------------------+-----------------+----------------+----------+
84
+	|  1 | sip:alice@domain | alice@live.com  | prpl-msn-pecan | password |
85
+	|  2 | sip:bob@domain   | bob@live.com    | prpl-msn-pecan | password |
86
+	|  3 | sip:alice@domain | alice@gmail.com | gtalk          | password |
87
+	|  4 | sip:bob@domain   | bob@gmail.com   | gtalk          | password |
88
+	+----+------------------+-----------------+----------------+----------+
89
+
90
+
91
+MySQL script :
92
+	CREATE TABLE purplemap (
93
+			id INT UNSIGNED PRIMARY KEY NOT NULL AUTO_INCREMENT,
94
+			sip_user VARCHAR(128) NOT NULL,
95
+			ext_user VARCHAR(128) NOT NULL,
96
+			ext_prot VARCHAR(16) NOT NULL,
97
+			ext_pass VARCHAR(64)
98
+	);
99
+
100
+
101
+
102
+
103
+Exported Parameters
104
+-------------------
105
+* db_url (string)
106
+modparam("purple", "db_url", "mysql://kamailio:kamailiorw@localhost/kamailio")
107
+
108
+* db_table (string)
109
+modparam("purple", "db_table", "purplemap")
110
+
111
+* httpProxy_host (string)
112
+modparam("purple", "httpProxy_host", "10.26.52.12")
113
+
114
+* httpProxy_port (int)
115
+modparam("purple", "httpProxy_port", 3128)
116
+
117
+
118
+Exported Functions
119
+------------------
120
+* purple_send_message
121
+In order to filter messages from purple and avoid loops, the tag proto=purple is appended to the R-URI.
122
+
123
+	if (is_method("MESSAGE")) {
124
+		xlog("MESSAGE $ru from <$fu> to <$tu>\n");
125
+		if (uri !~ "sip:.+@.+;proto=.+") {
126
+				xlog("FORWARDED to PURPLE\n");
127
+				purple_send_message();
128
+				if (!lookup("location")) {
129
+						sl_send_reply("200", "Accepted");
130
+						exit;
131
+				}
132
+		}
133
+	}
134
+
135
+
136
+* purple_handle_publish
137
+In order to filter publications from purple and avoid loops, the tag proto=purple is appended to the R-URI.
138
+
139
+	if(is_method("PUBLISH")) {
140
+			xlog("PUBLISH $ru from <$fu> to <$tu>\n");
141
+			if($hdr(Sender)!= NULL)
142
+					handle_publish("$hdr(Sender)");
143
+			else
144
+					handle_publish();
145
+			if (uri !~ "sip:.+@.+;proto=.+")
146
+					purple_handle_publish();
147
+			t_release();
148
+	}
149
+
150
+* purple_handle_subscribe
151
+
152
+	if(is_method("SUBSCRIBE")) {
153
+			xlog("SUBSCRIBE $ru from <$fu> to <$tu>\n");
154
+			handle_subscribe();
155
+			if ($hdr(Event) == "presence")
156
+					purple_handle_subscribe("$ruri", "$hdr(Expires)");
157
+			t_release();
158
+	}
159
+
160
+
161
+Limitations
162
+-----------
163
+* Doesn't implement authorization requests from external accounts to SIP.
164
+
0 165
new file mode 100644
... ...
@@ -0,0 +1,85 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#include <string.h>
20
+#include <libpurple/account.h>
21
+
22
+#include "../../dprint.h"
23
+
24
+#include "defines.h"
25
+#include "clientaccount.h"
26
+#include "mapping.h"
27
+
28
+extern PurpleProxyInfo *proxy;
29
+
30
+PurpleAccount *client_find_account(extern_account_t *account) {
31
+	PurpleAccount *r;
32
+
33
+	char* plugin;
34
+	char username[255];
35
+	memset(username, 0, 255);
36
+
37
+	if (strcmp(account->protocol, "gtalk") == 0) {
38
+		sprintf(username, "%s%s", account->username, "/sip");
39
+		plugin = "prpl-jabber";
40
+	}
41
+	else {
42
+		sprintf(username, "%s", account->username);
43
+		plugin = account->protocol;
44
+	}
45
+	
46
+
47
+	LM_DBG("searching purple account for %s with plugin %s \n", username, plugin);
48
+	r = purple_accounts_find(username, plugin);
49
+	if (r) {
50
+		LM_DBG("account %s found\n", username);
51
+		return r;
52
+	}
53
+
54
+	LM_DBG("account %s not found, creating.\n", username);
55
+	r = purple_account_new(username, plugin);
56
+	purple_account_set_password(r, account->password);
57
+	purple_account_set_remember_password(r, TRUE);
58
+
59
+	if (proxy != NULL)
60
+		purple_account_set_proxy_info(r, proxy);
61
+
62
+	if (strcmp(account->protocol, "gtalk") == 0)
63
+		purple_account_set_string(r, "connect_server", "talk.google.com");
64
+
65
+	purple_accounts_add(r);
66
+	
67
+	return r;
68
+}
69
+
70
+void client_enable_account(PurpleAccount *account) {
71
+
72
+	if ((account) && !purple_account_get_enabled(account, UI_ID)) {
73
+		LM_DBG("account %s disabled, enabling...\n", account->username);
74
+		purple_account_set_enabled(account, UI_ID, TRUE);
75
+	}
76
+
77
+	if ((account) && purple_account_is_disconnected(account)) {
78
+		LM_DBG("account %s disconnected, reconnecting...\n", account->username);
79
+		purple_account_connect(account);
80
+		LM_DBG("account %s connection called\n", account->username);
81
+	}
82
+}
83
+
84
+
0 85
new file mode 100644
... ...
@@ -0,0 +1,2 @@
0
+clientaccount.o clientaccount.d : clientaccount.c ../../dprint.h defines.h clientaccount.h \
1
+  mapping.h
0 2
new file mode 100644
... ...
@@ -0,0 +1,29 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#ifndef _CLIENTACCOUNT_H
20
+#define _CLIENTACCOUNT_H
21
+
22
+#include <libpurple/account.h>
23
+#include "mapping.h"
24
+
25
+PurpleAccount *client_find_account(extern_account_t *account);
26
+void client_enable_account(PurpleAccount *account);
27
+
28
+#endif
0 29
new file mode 100644
... ...
@@ -0,0 +1,61 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#include <stdlib.h>
20
+#include <string.h>
21
+#include <libpurple/conversation.h>
22
+
23
+#include "../../dprint.h"
24
+#include "../../mem/mem.h"
25
+
26
+#include "clientops.h"
27
+#include "purple.h"
28
+#include "purple_sip.h"
29
+#include "mapping.h"
30
+
31
+void write_conv(PurpleConversation *conv, const char *who, const char *alias, const char *message, PurpleMessageFlags flags, time_t mtime) {
32
+	char *sip_to, *sip_from;
33
+	purple_conversation_clear_message_history(conv);
34
+	if (flags == PURPLE_MESSAGE_RECV) {
35
+		LM_DBG("IM received from <%s> to <%s>\n", who, conv->account->username);
36
+		sip_to = find_sip_user(conv->account->username);
37
+		if (sip_to == NULL) {
38
+			LM_DBG("cannot retrieve sip uri for <%s>\n", conv->account->username);
39
+			return;
40
+		}
41
+		LM_DBG("<%s> translated to <%s>\n", conv->account->username, sip_to);
42
+
43
+		sip_from = find_sip_user((char*) who);
44
+		if (sip_from == NULL) {
45
+			LM_DBG("cannot retrieve sip uri for <%s>\n", who);
46
+			pkg_free(sip_to);
47
+			return;
48
+		}
49
+		LM_DBG("<%s> translated to <%s>\n", who, sip_from);
50
+		
51
+		LM_DBG("sending sip message\n");
52
+		if (purple_send_sip_msg(sip_to, sip_from, (char*) message) < 0)
53
+			LM_ERR("error sending sip message\n");
54
+		
55
+		pkg_free(sip_to);
56
+		pkg_free(sip_from);
57
+	}
58
+}
59
+
60
+
0 61
new file mode 100644
... ...
@@ -0,0 +1,3 @@
0
+clientops.o clientops.d : clientops.c ../../dprint.h ../../mem/mem.h \
1
+  ../../mem/../config.h ../../mem/../dprint.h ../../mem/f_malloc.h \
2
+  ../../mem/meminfo.h clientops.h purple.h purple_sip.h mapping.h
0 3
new file mode 100644
... ...
@@ -0,0 +1,29 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#ifndef _CLIENTOPS_H
20
+#define _CLIENTOPS_H
21
+
22
+#include <stdlib.h>
23
+#include <libpurple/conversation.h>
24
+
25
+
26
+void write_conv(PurpleConversation *conv, const char *who, const char *alias, const char *message, PurpleMessageFlags flags, time_t mtime);
27
+
28
+#endif
0 29
new file mode 100644
... ...
@@ -0,0 +1,256 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#include <string.h>
20
+#include <unistd.h>
21
+#include <stdlib.h>
22
+#include <errno.h>
23
+
24
+#include "../../dprint.h"
25
+
26
+#include "purple.h"
27
+#include "purplepipe.h"
28
+#include "purple_sip.h"
29
+#include "clientpipe.h"
30
+#include "mapping.h"
31
+#include "hashtable.h"
32
+#include "clientaccount.h"
33
+#include "utils.h"
34
+
35
+#include <libpurple/account.h>
36
+#include <libpurple/accountopt.h>
37
+#include <libpurple/conversation.h>
38
+#include <libpurple/connection.h>
39
+#include <libpurple/core.h>
40
+#include <libpurple/debug.h>
41
+#include <libpurple/eventloop.h>
42
+#include <libpurple/ft.h>
43
+#include <libpurple/log.h>
44
+#include <libpurple/notify.h>
45
+#include <libpurple/plugin.h>
46
+#include <libpurple/prefs.h>
47
+#include <libpurple/prpl.h>
48
+#include <libpurple/pounce.h>
49
+#include <libpurple/savedstatuses.h>
50
+#include <libpurple/sound.h>
51
+#include <libpurple/status.h>
52
+#include <libpurple/util.h>
53
+#include <libpurple/whiteboard.h>
54
+#include <libpurple/xmlnode.h>
55
+
56
+static void pipe_handle_message(struct purple_message *message) {
57
+	LM_DBG("handling message cmd\n");
58
+	PurpleAccount *account = NULL;
59
+	extern_account_t *accounts = NULL;
60
+	extern_user_t *users = NULL;
61
+	int naccounts = 0, nusers = 0;
62
+	int i, j;
63
+
64
+	PurpleConversation *conv = NULL;
65
+	LM_DBG("calling find_accounts(\"%s\", &naccounts)\n", message->from);
66
+	accounts = find_accounts(message->from, &naccounts);
67
+	LM_DBG("found %d extra account(s) for <%s>", naccounts, message->from);
68
+
69
+	LM_DBG("calling find_users(\"%s\", &nusers)\n", message->to);
70
+	users = find_users(message->to, &nusers);
71
+	LM_DBG("found %d extra user(s) for <%s>", nusers, message->to);
72
+
73
+	for (i = 0; i < naccounts; i++) {
74
+		LM_DBG("calling client_find_account(\"%s\")\n", accounts[i].username);
75
+		account = client_find_account(&accounts[i]);
76
+		if ((account) && purple_account_is_connected(account)) {
77
+			//enable_account(account);
78
+			for (j = 0; j < nusers; j++) {
79
+				if (!strcmp(accounts[i].protocol, users[j].protocol)) {
80
+					LM_DBG("mathing protocol found: %s\n", accounts[i].protocol);
81
+					conv = purple_find_conversation_with_account(PURPLE_CONV_TYPE_IM, users[j].username, account);
82
+					if (conv == NULL)
83
+						conv = purple_conversation_new(PURPLE_CONV_TYPE_IM, account, users[j].username);
84
+					purple_conv_im_send(purple_conversation_get_im_data(conv), message->body);
85
+					break;
86
+				}
87
+			}
88
+		}
89
+		else if (account == NULL)
90
+			LM_DBG("not account found neither created\n");
91
+		else if (purple_account_is_disconnected(account))
92
+			LM_DBG("account is disconnected cannot send message\n");
93
+	}
94
+	if (accounts)
95
+		extern_account_free(accounts, naccounts);
96
+	if (users)
97
+		extern_user_free(users, nusers);
98
+
99
+}
100
+
101
+static void pipe_handle_publish(struct purple_publish *publish) {
102
+	PurpleAccount *account = NULL;
103
+	extern_account_t *accounts = NULL;
104
+	int naccounts = 0;
105
+	int i;
106
+
107
+	LM_DBG("calling find_accounts(\"%s\", &naccoutns)\n", publish->from);
108
+	accounts = find_accounts(publish->from, &naccounts);
109
+	LM_DBG("found %d extra account(s) for <%s>", naccounts, publish->from);
110
+
111
+	for (i = 0; i < naccounts; i++) {
112
+		LM_DBG("calling client_find_account(\"%s\")\n", accounts[i].username);
113
+		account = client_find_account(&accounts[i]);
114
+		if (account) {
115
+		
116
+			if (publish->basic == PURPLE_BASIC_OPEN) {
117
+				client_enable_account(account);
118
+				LM_DBG("basic = open, setting up new status... %s,%d,%s\n", account[i].username, publish->primitive, publish->note);
119
+				PurpleStatusType *type = purple_account_get_status_type_with_primitive(account, publish->primitive);
120
+				if (purple_status_type_get_attr(type, "message")) {
121
+					purple_account_set_status(account, purple_status_type_get_id(type), TRUE, "message", publish->note, NULL);
122
+				} else {
123
+					purple_account_set_status(account, purple_status_type_get_id(type), TRUE, NULL);
124
+				}
125
+			}
126
+
127
+			else if (publish->basic == PURPLE_BASIC_CLOSED){
128
+				LM_DBG("basic = closed, setting up new status to offline... %s\n", account[i].username);
129
+				PurpleStatusType *type = purple_account_get_status_type_with_primitive(account, PURPLE_STATUS_OFFLINE);
130
+				purple_account_set_status(account, purple_status_type_get_id(type), TRUE, NULL);
131
+			}
132
+			
133
+		}
134
+	}
135
+
136
+	if (accounts)
137
+		extern_account_free(accounts, naccounts);
138
+
139
+}
140
+
141
+static void pipe_handle_subscribe(struct purple_subscribe *subscribe) {
142
+	PurpleAccount *account = NULL;
143
+	extern_account_t *accounts = NULL;
144
+	extern_user_t *users = NULL;
145
+	int naccounts = 0, nusers = 0;
146
+	int i, j;
147
+	PurpleBuddy *buddy = NULL;
148
+
149
+	int d = 0;
150
+
151
+	const char *note;
152
+	enum purple_publish_basic basic;
153
+	enum purple_publish_activity activity;
154
+
155
+	LM_DBG("calling find_accounts(\"%s\", &naccounts)\n", subscribe->from);
156
+	accounts = find_accounts(subscribe->from, &naccounts);
157
+	LM_DBG("found %d extra account(s) for <%s>", naccounts, subscribe->from);
158
+	
159
+	LM_DBG("calling find_users(\"%s\", &nusers)\n", subscribe->to);
160
+	users = find_users(subscribe->to, &nusers);
161
+	LM_DBG("found %d extra user(s) for <%s>", nusers, subscribe->to);
162
+
163
+	for (i = 0; i < naccounts; i++) {
164
+		LM_DBG("calling client_find_account(\"%s\")\n", accounts[i].username);
165
+		account = client_find_account(&accounts[i]);
166
+		//if ((account) && (purple_account_is_connected(account) || purple_account_is_connecting(account))) {
167
+		if (account) {
168
+			for (j = 0; j < nusers; j++) {
169
+				if (!strcmp(accounts[i].protocol, users[j].protocol)) {
170
+					LM_DBG("found matching protocol: %s\n", accounts[i].protocol);
171
+
172
+					LM_DBG("subscribe expires : %d\n", subscribe->expires);
173
+					if (subscribe->expires == 0)
174
+						d = hashtable_dec_counter(users[j].username);
175
+					else
176
+						d = hashtable_inc_counter(users[j].username);
177
+					
178
+					LM_DBG("<%s> is now referenced %d times\n", users[j].username, d);
179
+					if (d == 0) {
180
+						LM_DBG("<%s> is no more referenced, removing presence...\n", users[j].username);
181
+						if (purple_send_sip_publish(subscribe->to, users[j].username, PURPLE_BASIC_CLOSED, 0, NULL) < 0)
182
+							LM_ERR("error sending presence for %s", subscribe->to);
183
+						else
184
+							LM_DBG("presence message sent successfully\n");
185
+					}
186
+
187
+					else {
188
+	
189
+						buddy = purple_find_buddy(account, users[j].username);
190
+						if (buddy == NULL) {
191
+							LM_DBG("<%s> not found in <%s> buddy list, adding\n", users[j].username, accounts[i].username);
192
+							buddy = purple_buddy_new(account, users[j].username, users[j].username);
193
+							//purple_blist_add_buddy(buddy, NULL, NULL, NULL);
194
+							purple_account_add_buddy(account, buddy);
195
+						}
196
+						else {
197
+							LM_DBG("<%s> found in <%s> buddy list, sending publish\n", users[j].username, accounts[i].username);
198
+							PurplePresence *presence = purple_buddy_get_presence(buddy);
199
+							PurpleStatus *status = purple_presence_get_active_status(presence);
200
+							PurpleStatusType *type = purple_status_get_type(status);
201
+							PurpleStatusPrimitive primitive = purple_status_type_get_primitive(type);
202
+							note = purple_status_get_attr_string(status, "message");
203
+							primitive_parse(primitive, &basic, &activity);
204
+
205
+							if (purple_send_sip_publish(subscribe->to, users[j].username, basic, activity, note) < 0)
206
+								LM_ERR("error sending presence for %s", subscribe->to);
207
+							else
208
+								LM_DBG("presence message sent successfully\n");
209
+							
210
+						}	
211
+	
212
+					}
213
+
214
+					break;
215
+				}
216
+			}
217
+		}
218
+	}
219
+	if (accounts)
220
+		extern_account_free(accounts, naccounts);
221
+	if (users)
222
+		extern_user_free(users, nusers);
223
+	
224
+}
225
+
226
+void pipe_reader(gpointer data, gint fd, PurpleInputCondition condition) {
227
+	struct purple_cmd *cmd;
228
+	if (read(fd, &cmd, sizeof(cmd)) != sizeof(cmd)) {
229
+		LM_ERR("failed to read from command pipe: %s\n", strerror(errno));
230
+		return;
231
+	}
232
+	
233
+	switch (cmd->type) {
234
+	        case PURPLE_MESSAGE_CMD:
235
+		LM_DBG("received message cmd via pipe from <%s> to <%s>\n", cmd->message.from, cmd->message.to);
236
+		pipe_handle_message(&cmd->message);
237
+		break;
238
+
239
+		case PURPLE_SUBSCRIBE_CMD:
240
+		LM_DBG("received subscribe cmd via pipe from <%s> to <%s>\n", cmd->subscribe.from, cmd->subscribe.to);
241
+		pipe_handle_subscribe(&cmd->subscribe);
242
+		break;
243
+
244
+		case PURPLE_PUBLISH_CMD:
245
+		LM_DBG("received publish cmd via pipe from <%s>\n", cmd->publish.from);
246
+		pipe_handle_publish(&cmd->publish);
247
+		break;
248
+
249
+		default:
250
+		LM_ERR("unknown cmd type 0x%x\n", cmd->type);
251
+	}
252
+	purple_free_cmd(cmd);
253
+}
254
+
255
+
0 256
new file mode 100644
... ...
@@ -0,0 +1,3 @@
0
+clientpipe.o clientpipe.d : clientpipe.c ../../dprint.h purple.h purplepipe.h \
1
+  ../../str.h purple_sip.h clientpipe.h mapping.h hashtable.h \
2
+  clientaccount.h utils.h
0 3
new file mode 100644
... ...
@@ -0,0 +1,28 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#ifndef _CLIENTPIPE_H
20
+#define _CLIENTPIPE_H
21
+
22
+#include <glib.h>
23
+#include <libpurple/eventloop.h>
24
+
25
+void pipe_reader(gpointer data, gint fd, PurpleInputCondition condition);
26
+
27
+#endif
0 28
new file mode 100644
... ...
@@ -0,0 +1,209 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#include <glib.h>
20
+
21
+#include "../../dprint.h"
22
+#include "../../mem/mem.h"
23
+
24
+#include "defines.h"
25
+#include "clientsig.h"
26
+#include "purple.h"
27
+#include "purple_sip.h"
28
+#include "mapping.h"
29
+#include "hashtable.h"
30
+#include "utils.h"
31
+
32
+#include <libpurple/account.h>
33
+#include <libpurple/connection.h>
34
+#include <libpurple/status.h>
35
+
36
+static void signed_on(PurpleConnection *gc) {
37
+	LM_DBG("signed-on with <%s>\n", gc->account->username);
38
+}
39
+
40
+static void signing_on(PurpleConnection *gc) {
41
+	LM_DBG("signing-on with <%s>...\n", gc->account->username);
42
+}
43
+
44
+static void signed_off(PurpleConnection *gc) {
45
+	LM_DBG("signed-off with <%s>\n", gc->account->username);
46
+	purple_account_set_enabled(gc->account, UI_ID, FALSE);
47
+}
48
+
49
+static void signing_off(PurpleConnection *gc) {
50
+	LM_DBG("signing-off with <%s>...\n", gc->account->username);
51
+}
52
+
53
+static void account_error_changed(PurpleAccount *acc, const PurpleConnectionErrorInfo *old_error, const PurpleConnectionErrorInfo *current_error) {
54
+	if (current_error) {
55
+		LM_DBG("new account error : <%s>\n", current_error->description);
56
+	}
57
+}
58
+
59
+static void account_connecting(PurpleAccount *acc) {
60
+	LM_DBG("trying to connect with <%s>\n", acc->username);
61
+}
62
+
63
+static void account_enabled(PurpleAccount *acc) {
64
+	LM_DBG("account <%s> enabled...\n", acc->username);
65
+}
66
+
67
+static void account_disabled(PurpleAccount *acc) {
68
+	LM_DBG("account <%s> disabled...\n", acc->username);
69
+}
70
+
71
+
72
+static void buddy_status_changed(PurpleBuddy *buddy, PurpleStatus *old_status, PurpleStatus *status) {
73
+        PurplePlugin *prpl;
74
+        PurplePluginProtocolInfo *prpl_info = NULL;
75
+ 	char *sip_from = find_sip_user(buddy->name);
76
+	int d = hashtable_get_counter(buddy->name);
77
+	PurpleStatusPrimitive primitive;
78
+	enum purple_publish_basic basic;
79
+	enum purple_publish_activity activity;
80
+       	char *statustext = NULL, *tmp = NULL, *new;
81
+	const char *end;
82
+
83
+	LM_DBG("buddy <%s> has changed status\n", buddy->name);
84
+	if ((sip_from) && (d>0)) {
85
+		primitive = purple_status_type_get_primitive(purple_status_get_type(status));
86
+		primitive_parse(primitive, &basic, &activity);
87
+
88
+
89
+//		char *note = purple_status_get_attr_string(status, "message");
90
+
91
+	        prpl = purple_find_prpl(purple_account_get_protocol_id(buddy->account));
92
+
93
+		if (prpl != NULL)
94
+			prpl_info = PURPLE_PLUGIN_PROTOCOL_INFO(prpl);
95
+
96
+		if (prpl_info && prpl_info->status_text && buddy->account->gc) {
97
+			tmp = prpl_info->status_text(buddy);
98
+
99
+			if(tmp && !g_utf8_validate(tmp, -1, &end)) {
100
+				new = g_strndup(tmp, g_utf8_pointer_to_offset(tmp, end));
101
+				g_free(tmp);
102
+				tmp = new;
103
+			}
104
+
105
+			if(tmp) {
106
+				g_strdelimit(tmp, "\n", ' ');
107
+				purple_str_strip_char(tmp, '\r');
108
+			}
109
+			statustext = tmp;
110
+		}
111
+
112
+
113
+		LM_DBG("<%s> translated to <%s>, sending publish (note = %s)\n", buddy->name, sip_from, statustext);
114
+		purple_send_sip_publish(sip_from, buddy->name, basic, activity, statustext);
115
+
116
+		pkg_free(sip_from);
117
+		g_free(statustext);
118
+	}
119
+}
120
+
121
+static void buddy_signed_on(PurpleBuddy *buddy) {
122
+	char *sip_from;
123
+	int d;
124
+	LM_DBG("buddy <%s> signed on\n", buddy->name);
125
+	sip_from = find_sip_user(buddy->name);
126
+	if (sip_from) {
127
+		LM_DBG("<%s> translated to <%s>\n", buddy->name, sip_from);
128
+	}
129
+	else {
130
+		LM_DBG("cannot translate <%s>\n", buddy->name);
131
+		pkg_free(sip_from);
132
+		return;
133
+	}
134
+	d = hashtable_get_counter(buddy->name);
135
+	if (d>0) {
136
+		if (purple_send_sip_publish(sip_from, buddy->name, PURPLE_BASIC_OPEN, PURPLE_ACTIVITY_AVAILABLE, NULL) < 0)
137
+			LM_ERR("error sending PUBLISH for %s\n", buddy->name);
138
+		else 
139
+			LM_DBG("<%s> referenced %d times, PUBLISH sent\n", buddy->name, d);
140
+		pkg_free(sip_from);
141
+	}
142
+	else 
143
+		LM_DBG("%s is no more referenced, cannot publish\n", buddy->name);
144
+	
145
+}
146
+
147
+static void buddy_signed_off(PurpleBuddy *buddy) {
148
+	char *sip_from;
149
+	int d;
150
+	LM_DBG("buddy <%s> signed off\n", buddy->name);
151
+	sip_from = find_sip_user(buddy->name);
152
+	if (sip_from) {
153
+		LM_DBG("<%s> translated to <%s>\n", buddy->name, sip_from);
154
+	}
155
+	else {
156
+		LM_DBG("cannot translate <%s>\n", buddy->name);
157
+		pkg_free(sip_from);
158
+		return;
159
+	}
160
+	d = hashtable_get_counter(buddy->name);
161
+	if (d>0) {
162
+		if (purple_send_sip_publish(sip_from, buddy->name, PURPLE_BASIC_CLOSED, 0, NULL) < 0)
163
+			LM_ERR("error sending PUBLISH for %s\n", buddy->name);
164
+		else 
165
+			LM_DBG("<%s> referenced %d times, PUBLISH sent\n", buddy->name, d);
166
+		pkg_free(sip_from);
167
+	}
168
+	else 
169
+		LM_DBG("%s is no more referenced, cannot publish\n", buddy->name);
170
+	
171
+	
172
+}
173
+
174
+static void buddy_added(PurpleBuddy *buddy) {
175
+	LM_DBG("%s added to %s buddy list\n", buddy->name, buddy->account->username);
176
+}
177
+
178
+void client_connect_signals(void) {
179
+	static int handle;
180
+	purple_signal_connect(purple_connections_get_handle(), "signed-on", &handle,
181
+			PURPLE_CALLBACK(signed_on), NULL);
182
+	purple_signal_connect(purple_connections_get_handle(), "signed-off", &handle,
183
+			PURPLE_CALLBACK(signed_off), NULL);
184
+	purple_signal_connect(purple_connections_get_handle(), "signing-on", &handle,
185
+			PURPLE_CALLBACK(signing_on), NULL);
186
+	purple_signal_connect(purple_connections_get_handle(), "signing-off", &handle,
187
+			PURPLE_CALLBACK(signing_off), NULL);
188
+
189
+	purple_signal_connect(purple_accounts_get_handle(), "account-error-changed", &handle,
190
+			PURPLE_CALLBACK(account_error_changed), NULL);
191
+	purple_signal_connect(purple_accounts_get_handle(), "account-connecting", &handle,
192
+			PURPLE_CALLBACK(account_connecting), NULL);
193
+	purple_signal_connect(purple_accounts_get_handle(), "account-enabled", &handle,
194
+			PURPLE_CALLBACK(account_enabled), NULL);
195
+	purple_signal_connect(purple_accounts_get_handle(), "account-disabled", &handle,
196
+			PURPLE_CALLBACK(account_disabled), NULL);
197
+
198
+	purple_signal_connect(purple_blist_get_handle(), "buddy-signed-on", &handle,
199
+			PURPLE_CALLBACK(buddy_signed_on), NULL);
200
+	purple_signal_connect(purple_blist_get_handle(), "buddy-signed-off", &handle,
201
+			PURPLE_CALLBACK(buddy_signed_off), NULL);
202
+	purple_signal_connect(purple_blist_get_handle(), "buddy-status-changed", &handle,
203
+			PURPLE_CALLBACK(buddy_status_changed), NULL);
204
+	purple_signal_connect(purple_blist_get_handle(), "buddy-added", &handle,
205
+			PURPLE_CALLBACK(buddy_added), NULL);
206
+}
207
+
208
+
0 209
new file mode 100644
... ...
@@ -0,0 +1,48 @@
0
+clientsig.o clientsig.d : clientsig.c /usr/include/glib-2.0/glib.h \
1
+  /usr/include/glib-2.0/glib/galloca.h \
2
+  /usr/include/glib-2.0/glib/gtypes.h \
3
+  /usr/lib/glib-2.0/include/glibconfig.h \
4
+  /usr/include/glib-2.0/glib/gmacros.h \
5
+  /usr/include/glib-2.0/glib/garray.h \
6
+  /usr/include/glib-2.0/glib/gasyncqueue.h \
7
+  /usr/include/glib-2.0/glib/gthread.h \
8
+  /usr/include/glib-2.0/glib/gerror.h /usr/include/glib-2.0/glib/gquark.h \
9
+  /usr/include/glib-2.0/glib/gutils.h \
10
+  /usr/include/glib-2.0/glib/gatomic.h \
11
+  /usr/include/glib-2.0/glib/gbacktrace.h \
12
+  /usr/include/glib-2.0/glib/gbase64.h \
13
+  /usr/include/glib-2.0/glib/gbookmarkfile.h \
14
+  /usr/include/glib-2.0/glib/gcache.h /usr/include/glib-2.0/glib/glist.h \
15
+  /usr/include/glib-2.0/glib/gmem.h /usr/include/glib-2.0/glib/gslice.h \
16
+  /usr/include/glib-2.0/glib/gchecksum.h \
17
+  /usr/include/glib-2.0/glib/gcompletion.h \
18
+  /usr/include/glib-2.0/glib/gconvert.h \
19
+  /usr/include/glib-2.0/glib/gdataset.h \
20
+  /usr/include/glib-2.0/glib/gdate.h /usr/include/glib-2.0/glib/gdir.h \
21
+  /usr/include/glib-2.0/glib/gfileutils.h \
22
+  /usr/include/glib-2.0/glib/ghash.h /usr/include/glib-2.0/glib/ghook.h \
23
+  /usr/include/glib-2.0/glib/giochannel.h \
24
+  /usr/include/glib-2.0/glib/gmain.h /usr/include/glib-2.0/glib/gslist.h \
25
+  /usr/include/glib-2.0/glib/gstring.h \
26
+  /usr/include/glib-2.0/glib/gunicode.h \
27
+  /usr/include/glib-2.0/glib/gkeyfile.h \
28
+  /usr/include/glib-2.0/glib/gmappedfile.h \
29
+  /usr/include/glib-2.0/glib/gmarkup.h \
30
+  /usr/include/glib-2.0/glib/gmessages.h \
31
+  /usr/include/glib-2.0/glib/gnode.h /usr/include/glib-2.0/glib/goption.h \
32
+  /usr/include/glib-2.0/glib/gpattern.h \
33
+  /usr/include/glib-2.0/glib/gprimes.h \
34
+  /usr/include/glib-2.0/glib/gqsort.h /usr/include/glib-2.0/glib/gqueue.h \
35
+  /usr/include/glib-2.0/glib/grand.h /usr/include/glib-2.0/glib/grel.h \
36
+  /usr/include/glib-2.0/glib/gregex.h \
37
+  /usr/include/glib-2.0/glib/gscanner.h \
38
+  /usr/include/glib-2.0/glib/gsequence.h \
39
+  /usr/include/glib-2.0/glib/gshell.h /usr/include/glib-2.0/glib/gspawn.h \
40
+  /usr/include/glib-2.0/glib/gstrfuncs.h \
41
+  /usr/include/glib-2.0/glib/gtestutils.h \
42
+  /usr/include/glib-2.0/glib/gthreadpool.h \
43
+  /usr/include/glib-2.0/glib/gtimer.h /usr/include/glib-2.0/glib/gtree.h \
44
+  /usr/include/glib-2.0/glib/gurifuncs.h ../../dprint.h ../../mem/mem.h \
45
+  ../../mem/../config.h ../../mem/../dprint.h ../../mem/f_malloc.h \
46
+  ../../mem/meminfo.h defines.h clientsig.h purple.h purple_sip.h \
47
+  mapping.h hashtable.h utils.h
0 48
new file mode 100644
... ...
@@ -0,0 +1,25 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#ifndef _CLIENTSIG_H
20
+#define _CLIENTSIG_H
21
+
22
+void client_connect_signals(void);
23
+
24
+#endif
0 25
new file mode 100644
... ...
@@ -0,0 +1,28 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#ifndef _DEFINE_H
20
+#define _DEFINE_H
21
+
22
+#define		USER_DIRECTORY		"/dev/null"
23
+#define		PLUGIN_PATH		""
24
+#define		PLUGIN_PREF		"/purple/nullclient/plugins/saved"
25
+#define		UI_ID			"purpleser"
26
+
27
+#endif
0 28
new file mode 100644
... ...
@@ -0,0 +1,74 @@
0
+/* OpenSER PURPLE MODULE
1
+ * 
2
+ * Copyright (C) 2008 Atos Worldline
3
+ * Contact: Eric PTAK <eric.ptak@atosorigin.com>
4
+ *
5
+ * This program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 2 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * This program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
+ * GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public License
16
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
+ *
18
+ */
19
+#include <stdlib.h>