2013-01-16 13:43:48 +00:00
# -*- coding: utf-8 -*-
##############################################################################
#
# OpenERP, Open Source Management Solution
# Copyright (C) 2004-2010 Tiny SPRL (<http://tiny.be>).
#
# This program is free software: you can redistribute it and/or modify
2014-01-26 21:20:18 +00:00
# it under the terms of the GNU Affero General Public License as
2013-01-16 13:43:48 +00:00
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2014-01-26 21:20:18 +00:00
# GNU Affero General Public License for more details.
2013-01-16 13:43:48 +00:00
#
2014-01-26 21:20:18 +00:00
# You should have received a copy of the GNU Affero General Public License
2013-01-16 13:43:48 +00:00
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
##############################################################################
2013-01-29 15:05:56 +00:00
2013-02-04 16:37:20 +00:00
import random
2013-10-22 17:06:59 +00:00
import openerp
2014-09-19 09:35:26 +00:00
import json
2014-06-29 01:46:29 +00:00
import openerp . addons . im_chat . im_chat
2013-02-18 15:26:43 +00:00
from openerp . osv import osv , fields
from openerp import tools
2013-10-27 16:40:23 +00:00
from openerp import http
2013-10-22 17:06:59 +00:00
from openerp . http import request
2013-02-01 09:55:46 +00:00
2014-06-29 01:46:29 +00:00
class im_livechat_channel ( osv . Model ) :
2013-03-15 11:21:53 +00:00
_name = ' im_livechat.channel '
2013-02-05 14:52:54 +00:00
2013-02-13 09:07:14 +00:00
def _get_default_image ( self , cr , uid , context = None ) :
2013-03-15 11:21:53 +00:00
image_path = openerp . modules . get_module_resource ( ' im_livechat ' , ' static/src/img ' , ' default.png ' )
2013-02-13 09:07:14 +00:00
return tools . image_resize_image_big ( open ( image_path , ' rb ' ) . read ( ) . encode ( ' base64 ' ) )
def _get_image ( self , cr , uid , ids , name , args , context = None ) :
result = dict . fromkeys ( ids , False )
for obj in self . browse ( cr , uid , ids , context = context ) :
result [ obj . id ] = tools . image_get_resized_images ( obj . image )
return result
def _set_image ( self , cr , uid , id , name , value , args , context = None ) :
return self . write ( cr , uid , [ id ] , { ' image ' : tools . image_resize_image_big ( value ) } , context = context )
2013-02-05 14:52:54 +00:00
def _are_you_inside ( self , cr , uid , ids , name , arg , context = None ) :
res = { }
for record in self . browse ( cr , uid , ids , context = context ) :
res [ record . id ] = False
for user in record . user_ids :
2013-02-25 11:06:30 +00:00
if user . id == uid :
2013-02-05 14:52:54 +00:00
res [ record . id ] = True
break
return res
2014-06-29 01:46:29 +00:00
def _script_external ( self , cr , uid , ids , name , arg , context = None ) :
values = {
2014-10-01 14:46:03 +00:00
" url " : self . pool . get ( ' ir.config_parameter ' ) . get_param ( cr , openerp . SUPERUSER_ID , ' web.base.url ' ) ,
2014-06-29 01:46:29 +00:00
" dbname " : cr . dbname
}
res = { }
for record in self . browse ( cr , uid , ids , context = context ) :
values [ " channel " ] = record . id
res [ record . id ] = self . pool [ ' ir.ui.view ' ] . render ( cr , uid , ' im_livechat.external_loader ' , values , context = context )
return res
def _script_internal ( self , cr , uid , ids , name , arg , context = None ) :
values = {
2014-10-01 15:13:38 +00:00
" url " : self . pool . get ( ' ir.config_parameter ' ) . get_param ( cr , openerp . SUPERUSER_ID , ' web.base.url ' ) ,
2014-06-29 01:46:29 +00:00
" dbname " : cr . dbname
}
2013-02-05 15:15:06 +00:00
res = { }
for record in self . browse ( cr , uid , ids , context = context ) :
2014-06-29 01:46:29 +00:00
values [ " channel " ] = record . id
res [ record . id ] = self . pool [ ' ir.ui.view ' ] . render ( cr , uid , ' im_livechat.internal_loader ' , values , context = context )
2013-02-05 15:15:06 +00:00
return res
def _web_page ( self , cr , uid , ids , name , arg , context = None ) :
res = { }
for record in self . browse ( cr , uid , ids , context = context ) :
2014-09-30 12:05:02 +00:00
res [ record . id ] = self . pool . get ( ' ir.config_parameter ' ) . get_param ( cr , openerp . SUPERUSER_ID , ' web.base.url ' ) + \
2014-06-29 01:46:29 +00:00
" /im_livechat/support/ %s / %i " % ( cr . dbname , record . id )
2013-02-05 15:15:06 +00:00
return res
2013-02-01 09:55:46 +00:00
_columns = {
2014-06-29 01:46:29 +00:00
' name ' : fields . char ( string = " Channel Name " , size = 200 , required = True ) ,
2013-03-15 11:21:53 +00:00
' user_ids ' : fields . many2many ( ' res.users ' , ' im_livechat_channel_im_user ' , ' channel_id ' , ' user_id ' , string = " Users " ) ,
2013-02-05 14:52:54 +00:00
' are_you_inside ' : fields . function ( _are_you_inside , type = ' boolean ' , string = ' Are you inside the matrix? ' , store = False ) ,
2014-06-29 01:46:29 +00:00
' script_internal ' : fields . function ( _script_internal , type = ' text ' , string = ' Script (internal) ' , store = False ) ,
' script_external ' : fields . function ( _script_external , type = ' text ' , string = ' Script (external) ' , store = False ) ,
2014-07-06 14:44:26 +00:00
' web_page ' : fields . function ( _web_page , type = ' char ' , string = ' Web Page ' , store = False ) ,
' button_text ' : fields . char ( string = " Text of the Button " ) ,
' input_placeholder ' : fields . char ( string = " Chat Input Placeholder " ) ,
' default_message ' : fields . char ( string = " Welcome Message " , help = " This is an automated ' welcome ' message that your visitor will see when they initiate a new chat session. " ) ,
2013-02-13 09:07:14 +00:00
# image: all image fields are base64 encoded and PIL-supported
' image ' : fields . binary ( " Photo " ,
help = " This field holds the image used as photo for the group, limited to 1024x1024px. " ) ,
' image_medium ' : fields . function ( _get_image , fnct_inv = _set_image ,
string = " Medium-sized photo " , type = " binary " , multi = " _get_image " ,
store = {
2013-03-15 11:21:53 +00:00
' im_livechat.channel ' : ( lambda self , cr , uid , ids , c = { } : ids , [ ' image ' ] , 10 ) ,
2013-02-13 09:07:14 +00:00
} ,
help = " Medium-sized photo of the group. It is automatically " \
" resized as a 128x128px image, with aspect ratio preserved. " \
" Use this field in form views or some kanban views. " ) ,
' image_small ' : fields . function ( _get_image , fnct_inv = _set_image ,
string = " Small-sized photo " , type = " binary " , multi = " _get_image " ,
store = {
2013-03-15 11:21:53 +00:00
' im_livechat.channel ' : ( lambda self , cr , uid , ids , c = { } : ids , [ ' image ' ] , 10 ) ,
2013-02-13 09:07:14 +00:00
} ,
help = " Small-sized photo of the group. It is automatically " \
" resized as a 64x64px image, with aspect ratio preserved. " \
" Use this field anywhere a small image is required. " ) ,
2013-02-11 09:55:10 +00:00
}
2013-02-13 14:38:52 +00:00
def _default_user_ids ( self , cr , uid , context = None ) :
2013-02-25 11:06:30 +00:00
return [ ( 6 , 0 , [ uid ] ) ]
2013-02-13 14:38:52 +00:00
2013-02-11 09:55:10 +00:00
_defaults = {
2013-02-13 11:04:20 +00:00
' button_text ' : " Have a Question? Chat with us. " ,
2013-02-11 09:55:10 +00:00
' input_placeholder ' : " How may I help you? " ,
' default_message ' : ' ' ,
2013-02-13 14:38:52 +00:00
' user_ids ' : _default_user_ids ,
2013-02-13 09:07:14 +00:00
' image ' : _get_default_image ,
2013-02-04 15:36:12 +00:00
}
2013-09-02 12:23:11 +00:00
def get_available_users ( self , cr , uid , channel_id , context = None ) :
2014-06-29 01:46:29 +00:00
""" get available user of a given channel """
channel = self . browse ( cr , uid , channel_id , context = context )
2013-02-04 16:37:20 +00:00
users = [ ]
2014-06-29 01:46:29 +00:00
for user_id in channel . user_ids :
if ( user_id . im_status == ' online ' ) :
users . append ( user_id )
2013-09-02 12:23:11 +00:00
return users
2014-06-29 01:46:29 +00:00
def get_channel_session ( self , cr , uid , channel_id , anonymous_name , context = None ) :
""" return a session given a channel : create on with a registered user, or return false otherwise """
# get the avalable user of the channel
users = self . get_available_users ( cr , uid , channel_id , context = context )
2013-02-04 16:37:20 +00:00
if len ( users ) == 0 :
return False
2013-09-02 12:23:11 +00:00
user_id = random . choice ( users ) . id
2014-06-29 01:46:29 +00:00
# create the session, and add the link with the given channel
Session = self . pool [ " im_chat.session " ]
newid = Session . create ( cr , uid , { ' user_ids ' : [ ( 4 , user_id ) ] , ' channel_id ' : channel_id , ' anonymous_name ' : anonymous_name } , context = context )
return Session . session_info ( cr , uid , [ newid ] , context = context )
2013-02-04 16:37:20 +00:00
2013-02-13 10:43:21 +00:00
def test_channel ( self , cr , uid , channel , context = None ) :
if not channel :
return { }
return {
' url ' : self . browse ( cr , uid , channel [ 0 ] , context = context or { } ) . web_page ,
' type ' : ' ir.actions.act_url '
}
2013-02-11 09:55:10 +00:00
def get_info_for_chat_src ( self , cr , uid , channel , context = None ) :
2014-06-29 01:46:29 +00:00
url = self . pool . get ( ' ir.config_parameter ' ) . get_param ( cr , uid , ' web.base.url ' )
2013-02-11 09:55:10 +00:00
chan = self . browse ( cr , uid , channel , context = context )
return {
" url " : url ,
' buttonText ' : chan . button_text ,
' inputPlaceholder ' : chan . input_placeholder ,
' defaultMessage ' : chan . default_message ,
2013-02-11 13:47:23 +00:00
" channelName " : chan . name ,
2013-02-11 09:55:10 +00:00
}
2013-02-05 13:47:11 +00:00
2013-02-05 14:52:54 +00:00
def join ( self , cr , uid , ids , context = None ) :
2013-02-25 11:06:30 +00:00
self . write ( cr , uid , ids , { ' user_ids ' : [ ( 4 , uid ) ] } )
2013-02-05 14:52:54 +00:00
return True
def quit ( self , cr , uid , ids , context = None ) :
2013-02-25 11:06:30 +00:00
self . write ( cr , uid , ids , { ' user_ids ' : [ ( 3 , uid ) ] } )
2013-02-05 14:52:54 +00:00
return True
2014-06-29 01:46:29 +00:00
class im_chat_session ( osv . Model ) :
_inherit = ' im_chat.session '
def _get_fullname ( self , cr , uid , ids , fields , arg , context = None ) :
""" built the complete name of the session """
result = { }
sessions = self . browse ( cr , uid , ids , context = context )
for session in sessions :
names = [ ]
for user in session . user_ids :
names . append ( user . name )
if session . anonymous_name :
names . append ( session . anonymous_name )
result [ session . id ] = ' , ' . join ( names )
return result
2013-02-13 11:08:10 +00:00
_columns = {
2014-06-29 01:46:29 +00:00
' anonymous_name ' : fields . char ( ' Anonymous Name ' ) ,
[FIX] im_livechat: many2one channel_id of im_session to the right model.
In im_session model, field channel_id was a many2one to im_user, or, obviously, this should be a many2one to im_livechat.channel
Well, obviously, this is a copy/paste error (or distraction, your choice!). This fix should normally not be pushed on a stable branch (like the current one, saas-2), but considering the severity of the problem, and the few changes in database (alter foreign key only), this is acceptable. Why such a big mistake has not been seen earlier ? Do you even test or read back what you write ?
bzr revid: dle@openerp.com-20131204122727-q0ch5j2v8rrli41e
2013-12-04 12:27:27 +00:00
' channel_id ' : fields . many2one ( " im_livechat.channel " , " Channel " ) ,
2014-06-29 01:46:29 +00:00
' fullname ' : fields . function ( _get_fullname , type = " char " , string = " Complete name " ) ,
2013-02-13 11:08:10 +00:00
}
2014-06-29 01:46:29 +00:00
2014-09-19 09:35:26 +00:00
def is_in_session ( self , cr , uid , uuid , user_id , context = None ) :
""" return if the given user_id is in the session """
sids = self . search ( cr , uid , [ ( ' uuid ' , ' = ' , uuid ) ] , context = context , limit = 1 )
for session in self . browse ( cr , uid , sids , context = context ) :
2014-09-25 14:30:50 +00:00
if session . anonymous_name and user_id == openerp . SUPERUSER_ID :
2014-09-19 09:35:26 +00:00
return True
else :
return super ( im_chat_session , self ) . is_in_session ( cr , uid , uuid , user_id , context = context )
2014-09-22 08:41:11 +00:00
return False
2014-09-19 09:35:26 +00:00
2014-06-29 01:46:29 +00:00
def users_infos ( self , cr , uid , ids , context = None ) :
""" add the anonymous user in the user of the session """
for session in self . browse ( cr , uid , ids , context = context ) :
users_infos = super ( im_chat_session , self ) . users_infos ( cr , uid , ids , context = context )
if session . anonymous_name :
users_infos . append ( { ' id ' : False , ' name ' : session . anonymous_name , ' im_status ' : ' online ' } )
return users_infos
class LiveChatController ( http . Controller ) :
@http.route ( ' /im_livechat/support/<string:dbname>/<int:channel_id> ' , type = ' http ' , auth = ' none ' )
def support_page ( self , dbname , channel_id , * * kwargs ) :
registry , cr , uid , context = openerp . modules . registry . RegistryManager . get ( dbname ) , request . cr , openerp . SUPERUSER_ID , request . context
info = registry . get ( ' im_livechat.channel ' ) . get_info_for_chat_src ( cr , uid , channel_id )
info [ " dbname " ] = dbname
info [ " channel " ] = channel_id
info [ " channel_name " ] = registry . get ( ' im_livechat.channel ' ) . read ( cr , uid , channel_id , [ ' name ' ] , context = context ) [ " name " ]
return request . render ( ' im_livechat.support_page ' , info )
@http.route ( ' /im_livechat/loader/<string:dbname>/<int:channel_id> ' , type = ' http ' , auth = ' none ' )
def loader ( self , dbname , channel_id , * * kwargs ) :
registry , cr , uid , context = openerp . modules . registry . RegistryManager . get ( dbname ) , request . cr , openerp . SUPERUSER_ID , request . context
info = registry . get ( ' im_livechat.channel ' ) . get_info_for_chat_src ( cr , uid , channel_id )
info [ " dbname " ] = dbname
info [ " channel " ] = channel_id
info [ " username " ] = kwargs . get ( " username " , " Visitor " )
return request . render ( ' im_livechat.loader ' , info )
@http.route ( ' /im_livechat/get_session ' , type = " json " , auth = " none " )
2014-09-25 14:30:50 +00:00
def get_session ( self , channel_id , anonymous_name , * * kwargs ) :
2014-06-29 01:46:29 +00:00
cr , uid , context , db = request . cr , request . uid or openerp . SUPERUSER_ID , request . context , request . db
reg = openerp . modules . registry . RegistryManager . get ( db )
# if geoip, add the country name to the anonymous name
if hasattr ( request , ' geoip ' ) :
anonymous_name = anonymous_name + " ( " + request . geoip . get ( ' country_name ' , " " ) + " ) "
return reg . get ( " im_livechat.channel " ) . get_channel_session ( cr , uid , channel_id , anonymous_name , context = context )
@http.route ( ' /im_livechat/available ' , type = ' json ' , auth = " none " )
def available ( self , db , channel ) :
cr , uid , context , db = request . cr , request . uid or openerp . SUPERUSER_ID , request . context , request . db
reg = openerp . modules . registry . RegistryManager . get ( db )
with reg . cursor ( ) as cr :
return len ( reg . get ( ' im_livechat.channel ' ) . get_available_users ( cr , uid , channel ) ) > 0
2014-09-19 09:35:26 +00:00