[MERGE] sync with latest trunk

bzr revid: odo@openerp.com-20110930122511-ddjsuqmwn0mr1p5q
This commit is contained in:
Olivier Dony 2011-09-30 14:25:11 +02:00
commit a5b7faffb3
15 changed files with 398 additions and 257 deletions

View File

@ -290,6 +290,7 @@ CREATE TABLE ir_module_module (
state character varying(16),
latest_version character varying(64),
shortdesc character varying(256),
complexity character varying(32),
category_id integer REFERENCES ir_module_category ON DELETE SET NULL,
certificate character varying(64),
description text,

View File

@ -1006,7 +1006,7 @@
</record>
<record id="main_partner" model="res.partner">
<field name="name">Company Name</field>
<field name="name">Your Company</field>
<!-- Address and Company ID will be set later -->
<field name="address" eval="[]"/>
<field name="company_id" eval="None"/>
@ -1014,14 +1014,7 @@
</record>
<record id="main_address" model="res.partner.address">
<field name="partner_id" ref="main_partner"/>
<field name="name">Company contact name</field>
<field name="street">Company street, number</field>
<field name="zip">Company zip</field>
<field name="city">Company city</field>
<field name="phone">+1-212-555-12345</field>
<field name="type">default</field>
<field model="res.country" name="country_id" ref="us"/>
<!-- Company ID will be set later -->
<field name="company_id" eval="None"/>
</record>
@ -1042,7 +1035,7 @@
<!-- Basic Company -->
<record id="main_company" model="res.company">
<field name="name">Company Name</field>
<field name="name">Your Company</field>
<field name="partner_id" ref="main_partner"/>
<field name="rml_header1">Company business slogan</field>
<field name="rml_footer1">Web: www.companyname.com - Tel: +1-212-555-12345</field>

View File

@ -209,7 +209,7 @@
<group colspan="4" col="6">
<group colspan="4" col="4">
<field name="name"/>
<field name="partner_id" readonly="1" required="0"/>
<field name="partner_id" readonly="1" required="0" groups="base.group_extended"/>
<field name="parent_id" groups="base.group_multi_company"/>
</group>
<group colspan="2" col="2">
@ -225,18 +225,17 @@
<field name="city"/>
<field name="country_id"/>
<field name="state_id"/>
<field name="phone"/>
<field name="email"/>
<field name="fax"/>
<field name="website"/>
<field name="vat"/>
<field name="company_registry"/>
<field name="phone" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<field name="email" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<field name="fax" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<field name="website" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<field name="vat" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<field name="company_registry" on_change="on_change_header(phone, email, fax, website, vat, company_registry)"/>
<separator string="Header/Footer of Reports" colspan="4"/>
<group colspan="4" col="3">
<field name="rml_header1" colspan="3"/>
<newline/>
<field name="rml_footer1" colspan="2"/>
<button name="generate_header" string="Generate" type="object" icon="gtk-go-forward"/>
<field name="rml_footer1" colspan="3" groups="base.group_extended"/>
<newline/>
<field name="rml_footer2" colspan="2"/>
<button name="%(bank_account_update)d" string="Set Bank Accounts" type="action" icon="gtk-go-forward"/>
@ -245,10 +244,10 @@
<button name="%(preview_report)d" string="Preview Header" type="action" icon="gtk-print"/>
</group>
</page>
<page string="External Template" groups="base.group_extended">
<page string="Header/Footer" groups="base.group_extended">
<field colspan="4" name="rml_header" nolabel="1"/>
</page>
<page string="Internal Template" groups="base.group_extended">
<page string="Internal Header/Footer" groups="base.group_extended">
<separator string="Portrait" colspan="2"/>
<separator string="Landscape" colspan="2"/>
<field colspan="2" name="rml_header2" nolabel="1"/>

File diff suppressed because it is too large Load Diff

View File

@ -7,14 +7,14 @@ msgstr ""
"Project-Id-Version: OpenERP Server 5.0.0\n"
"Report-Msgid-Bugs-To: support@openerp.com\n"
"POT-Creation-Date: 2011-01-11 11:14+0000\n"
"PO-Revision-Date: 2011-09-27 16:28+0000\n"
"PO-Revision-Date: 2011-09-29 15:26+0000\n"
"Last-Translator: Walter Cheuk <wwycheuk@gmail.com>\n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2011-09-28 05:19+0000\n"
"X-Generator: Launchpad (build 14049)\n"
"X-Launchpad-Export-Date: 2011-09-30 04:37+0000\n"
"X-Generator: Launchpad (build 14071)\n"
#. module: base
#: view:ir.filters:0
@ -2795,7 +2795,7 @@ msgstr "向用戶提供目標視窗之額外說明文字,如其用法及用途
#. module: base
#: model:res.country,name:base.va
msgid "Holy See (Vatican City State)"
msgstr "教廷(梵蒂岡)"
msgstr "教廷 (梵蒂岡)"
#. module: base
#: field:base.module.import,module_file:0
@ -5754,7 +5754,7 @@ msgstr "一年中的星期:%(woy)s"
#. module: base
#: model:res.partner.category,name:base.res_partner_category_14
msgid "Bad customers"
msgstr "客戶"
msgstr "客戶"
#. module: base
#: report:ir.module.reference.graph:0

View File

@ -88,6 +88,18 @@ class res_company(osv.osv):
result[company.id][field] = address[field] or False
return result
def _get_bank_data(self, cr, uid, ids, field_names, arg, context=None):
""" Read the 'address' functional fields. """
result = {}
for company in self.browse(cr, uid, ids, context=context):
r = []
for bank in company.bank_ids:
if bank.footer:
r.append(bank.name_get(context=context)[0][1])
result[company.id] = ' | '.join(r)
return result
def _set_address_data(self, cr, uid, company_id, name, value, arg, context=None):
""" Write the 'address' functional fields. """
company = self.browse(cr, uid, company_id, context=context)
@ -102,19 +114,9 @@ class res_company(osv.osv):
address_obj.create(cr, uid, {name: value or False, 'partner_id': company.partner_id.id}, context=context)
return True
def _get_bank_data(self, cr, uid, ids, field_names, arg, context=None):
""" Read the 'address' functional fields. """
result = {}
for company in self.browse(cr, uid, ids, context=context):
r = []
for bank in company.bank_ids:
if bank.footer:
r.append(bank.name_get(context=context)[0][1])
result[company.id] = ' | '.join(r)
return result
_columns = {
'name': fields.char('Company Name', size=64, required=True),
'name': fields.related('partner_id', 'name', string='Company Name', size=64, required=True, store=True, type='char'),
'parent_id': fields.many2one('res.company', 'Parent Company', select=True),
'child_ids': fields.one2many('res.company', 'parent_id', 'Child Companies'),
'partner_id': fields.many2one('res.partner', 'Partner', required=True),
@ -146,6 +148,15 @@ class res_company(osv.osv):
_sql_constraints = [
('name_uniq', 'unique (name)', 'The company name must be unique !')
]
def on_change_header(self, cr, uid, ids, phone, email, fax, website, vat, reg=False, context={}):
val = []
if phone: val.append(_('Phone: ')+phone)
if fax: val.append(_('Fax: ')+fax)
if website: val.append(_('Website: ')+website)
if vat: val.append(_('VAT: ')+vat)
if reg: val.append(_('Reg: ')+reg)
return {'value': {'rml_footer1':' | '.join(val)}}
def _search(self, cr, uid, args, offset=0, limit=None, order=None,
context=None, count=False, access_rights_uid=None):
@ -228,16 +239,6 @@ class res_company(osv.osv):
self.cache_restart(cr)
return super(res_company, self).write(cr, *args, **argv)
def generate_header(self, cr, uid, ids, context=None):
for c in self.browse(cr, uid, ids, context=context):
val = []
if c.phone: val.append(_('Phone: ')+c.phone)
if c.fax: val.append(_('Fax: ')+c.fax)
if c.website: val.append(_('Website: ')+c.website)
if c.vat: val.append(_('VAT: ')+c.vat)
if c.company_registry: val.append(_('Reg: ')+c.company_registry)
self.write(cr,uid, [c.id], {'rml_footer1':' | '.join(val)}, context)
def _get_euro(self, cr, uid, context={}):
try:
return self.pool.get('res.currency').search(cr, uid, [])[0]

View File

@ -133,12 +133,15 @@ notifications, such as the availability of invoices."),
'customer': fields.boolean('Customer', help="Check this box if the partner is a customer."),
'supplier': fields.boolean('Supplier', help="Check this box if the partner is a supplier. If it's not checked, purchase people will not see it when encoding a purchase order."),
'city': fields.related('address', 'city', type='char', string='City'),
'function': fields.related('address', 'function', type='char', string='function'),
'subname': fields.related('address', 'name', type='char', string='Contact Name'),
'phone': fields.related('address', 'phone', type='char', string='Phone'),
'mobile': fields.related('address', 'mobile', type='char', string='Mobile'),
'country': fields.related('address', 'country_id', type='many2one', relation='res.country', string='Country'),
'employee': fields.boolean('Employee', help="Check this box if the partner is an Employee."),
'email': fields.related('address', 'email', type='char', size=240, string='E-mail'),
'company_id': fields.many2one('res.company', 'Company', select=1),
'color': fields.integer('Color Index'),
}
def _default_category(self, cr, uid, context={}):
@ -153,6 +156,7 @@ notifications, such as the availability of invoices."),
'category_id': _default_category,
'company_id': lambda s,cr,uid,c: s.pool.get('res.company')._company_default_get(cr, uid, 'res.partner', context=c),
'opt_out' : False,
'color': 0,
}
def copy(self, cr, uid, id, default={}, context={}):
@ -303,6 +307,7 @@ class res_partner_address(osv.osv):
'active': fields.boolean('Active', help="Uncheck the active field to hide the contact."),
# 'company_id': fields.related('partner_id','company_id',type='many2one',relation='res.company',string='Company', store=True),
'company_id': fields.many2one('res.company', 'Company',select=1),
'color': fields.integer('Color Index'),
}
_defaults = {
'active': lambda *a: 1,

View File

@ -105,11 +105,80 @@
</form>
</field>
</record>
<record model="ir.ui.view" id="contacts_kanban_view">
<field name="name">res.partner.address.kanban</field>
<field name="model">res.partner.address</field>
<field name="type">kanban</field>
<field name="arch" type="xml">
<kanban >
<templates>
<t t-name="kanban-box">
<t t-set="color" t-value="kanban_color(record.color.raw_value || record.name.raw_value)"/>
<div t-att-class="color + (record.color.raw_value == 1 ? ' oe_kanban_color_alert' : '')">
<div class="oe_kanban_box oe_kanban_color_border">
<div class="oe_kanban_box_header oe_kanban_color_bgdark oe_kanban_color_border oe_kanban_draghandle">
<table class="oe_kanban_table">
<tr>
<td class="oe_kanban_title1" align="left" valign="middle">
<field name="name"/>
</td>
<td valign="top" width="22">
<img t-att-src="kanban_gravatar(record.email.value, 22)" class="oe_kanban_gravatar"/>
</td>
</tr>
</table>
</div>
<div class="oe_kanban_box_content oe_kanban_color_bglight oe_kanban_box_show_onclick_trigger oe_kanban_color_border">
<table class="oe_kanban_table">
<tr>
<td valign="top" width="22" align="left">
<img src="/web/static/src/img/persons.png"/>
</td>
<td valign="top" align="left">
<div class="oe_kanban_title2">
<field name="title"/>
<t t-if="record.title.raw_value &amp;&amp; record.function.raw_value">,</t>
<field name="function"/>
</div>
<div class="oe_kanban_title3">
<field name="partner_id"/>
<t t-if="record.partner_id.raw_value &amp;&amp; record.country_id.raw_value">,</t>
<field name="country_id"/>
</div>
<div class="oe_kanban_title3">
<i><field name="email"/>
<t t-if="record.phone.raw_value &amp;&amp; record.email.raw_value">,</t>
<field name="phone"/></i>
</div>
</td>
</tr>
</table>
</div>
<div class="oe_kanban_buttons_set oe_kanban_color_border oe_kanban_color_bglight oe_kanban_box_show_onclick">
<div class="oe_kanban_left">
<a string="Edit" icon="gtk-edit" type="edit"/>
<a string="Change Color" icon="color-picker" type="color" name="color"/>
<a title="Mail" t-att-href="'mailto:'+record.email.value" style="text-decoration: none;" >
<img src="/web/static/src/img/icons/terp-mail-message-new.png" border="0" width="16" height="16"/>
</a>
</div>
<br class="oe_kanban_clear"/>
</div>
</div>
</div>
</t>
</templates>
</kanban>
</field>
</record>
<record id="action_partner_address_form" model="ir.actions.act_window">
<field name="name">Addresses</field>
<field name="type">ir.actions.act_window</field>
<field name="res_model">res.partner.address</field>
<field name="view_type">form</field>
<field name="view_mode">tree,form,kanban</field>
<field name="context">{"search_default_customer":1}</field>
<field name="search_view_id" ref="view_res_partner_address_filter"/>
<field name="help">Customers (also called Partners in other areas of the system) helps you manage your address book of companies whether they are prospects, customers and/or suppliers. The partner form allows you to track and record all the necessary information to interact with your partners from the company address to their contacts as well as pricelists, and much more. If you installed the CRM, with the history tab, you can track all the interactions with a partner such as opportunities, emails, or sales orders issued.</field>
@ -354,12 +423,81 @@
</search>
</field>
</record>
<!-- Partner Kanban View -->
<record model="ir.ui.view" id="res_partner_kanban_view">
<field name="name">RES - PARTNER KANBAN</field>
<field name="model">res.partner</field>
<field name="type">kanban</field>
<field name="arch" type="xml">
<kanban>
<templates>
<t t-name="kanban-box">
<t t-set="color" t-value="kanban_color(record.color.raw_value || record.name.raw_value)"/>
<div t-att-class="color + (record.color.raw_value == 1 ? ' oe_kanban_color_alert' : '')">
<div class="oe_kanban_box oe_kanban_color_border">
<div class="oe_kanban_box_header oe_kanban_color_bgdark oe_kanban_color_border oe_kanban_draghandle">
<table class="oe_kanban_table">
<tr>
<td class="oe_kanban_title1" align="left" valign="middle">
<field name="name"/>
</td>
<td valign="top" width="22">
<img t-att-src="kanban_gravatar(record.email.value, 22)" class="oe_kanban_gravatar"/>
</td>
</tr>
</table>
</div>
<div class="oe_kanban_box_content oe_kanban_color_bglight oe_kanban_box_show_onclick_trigger oe_kanban_color_border">
<table class="oe_kanban_table">
<tr>
<td valign="top" width="22" align="left">
<img src="/web/static/src/img/partner.png"/>
</td>
<td valign="top" align="left">
<div class="oe_kanban_title2">
<field name="title"/>
<t t-if="record.title.raw_value &amp;&amp; record.country.raw_value">,</t>
<field name="country"/>
</div>
<div class="oe_kanban_title3">
<field name="subname"/>
<t t-if="record.subname.raw_value &amp;&amp; record.function.raw_value">,</t>
<field name="function"/>
</div>
<div class="oe_kanban_title3">
<i><field name="email"/>
<t t-if="record.phone.raw_value &amp;&amp; record.email.raw_value">,</t>
<field name="phone"/></i>
</div>
</td>
</tr>
</table>
</div>
<div class="oe_kanban_buttons_set oe_kanban_color_border oe_kanban_color_bglight oe_kanban_box_show_onclick">
<div class="oe_kanban_left">
<a string="Edit" icon="gtk-edit" type="edit"/>
<a string="Change Color" icon="color-picker" type="color" name="color"/>
<a title="Mail" t-att-href="'mailto:'+record.email.value" style="text-decoration: none;" >
<img src="/web/static/src/img/icons/terp-mail-message-new.png" border="0" width="16" height="16"/>
</a>
</div>
<br class="oe_kanban_clear"/>
</div>
</div>
</div>
</t>
</templates>
</kanban>
</field>
</record>
<record id="action_partner_form" model="ir.actions.act_window">
<field name="name">Customers</field>
<field name="type">ir.actions.act_window</field>
<field name="res_model">res.partner</field>
<field name="view_type">form</field>
<field name="view_mode">kanban</field>
<field name="context">{"search_default_customer":1}</field>
<field name="search_view_id" ref="view_res_partner_filter"/>
<field name="help">A customer is an entity you do business with, like a company or an organization. A customer can have several contacts or addresses which are the people working for this company. You can use the history tab, to follow all transactions related to a customer: sales order, emails, opportunities, claims, etc. If you use the email gateway, the Outlook or the Thunderbird plugin, don't forget to register emails to each contact so that the gateway will automatically attach incoming emails to the right partner.</field>

View File

@ -75,13 +75,14 @@ def initialize(cr):
cr.execute('INSERT INTO ir_module_module \
(author, website, name, shortdesc, description, \
category_id, state, certificate, web, license) \
VALUES (%s, %s, %s, %s, %s, %s, %s, %s, %s, %s) RETURNING id', (
category_id, state, certificate, web, license, complexity) \
VALUES (%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s) RETURNING id', (
info['author'],
info['website'], i, info['name'],
info['description'], category_id, state, info['certificate'],
info['web'],
info['license']))
info['license'],
info['complexity']))
id = cr.fetchone()[0]
cr.execute('INSERT INTO ir_model_data \
(name,model,module, res_id, noupdate) VALUES (%s,%s,%s,%s,%s)', (

View File

@ -249,6 +249,7 @@ def load_information_from_description_file(module):
info.setdefault('website', '')
info.setdefault('name', False)
info.setdefault('description', '')
info.setdefault('complexity', False)
info['certificate'] = info.get('certificate') or None
info['web'] = info.get('web') or False
info['license'] = info.get('license') or 'AGPL-3'

View File

@ -1285,7 +1285,7 @@ class property(function):
self.field_id = {}
def field_to_dict(self, cr, user, context, field):
def field_to_dict(model, cr, user, field, context=None):
""" Return a dictionary representation of a field.
The string, help, and selection attributes (if any) are untranslated. This
@ -1308,8 +1308,9 @@ def field_to_dict(self, cr, user, context, field):
res['fnct_inv_arg'] = field._fnct_inv_arg or False
res['func_obj'] = field._obj or False
if isinstance(field, many2many):
res['related_columns'] = list((field._id1, field._id2))
res['third_table'] = field._rel
(table, col1, col2) = field._sql_names(model)
res['related_columns'] = [col1, col2]
res['third_table'] = table
for arg in ('string', 'readonly', 'states', 'size', 'required', 'group_operator',
'change_default', 'translate', 'help', 'select', 'selectable'):
if getattr(field, arg):
@ -1328,7 +1329,7 @@ def field_to_dict(self, cr, user, context, field):
res['selection'] = field.selection
else:
# call the 'dynamic selection' function
res['selection'] = field.selection(self, cr, user, context)
res['selection'] = field.selection(model, cr, user, context)
if res['type'] in ('one2many', 'many2many', 'many2one', 'one2one'):
res['relation'] = field._obj
res['domain'] = field._domain

View File

@ -2069,8 +2069,9 @@ class BaseModel(object):
context)
resprint = map(clean, resprint)
resaction = map(clean, resaction)
resaction = filter(lambda x: not x.get('multi', False), resaction)
resprint = filter(lambda x: not x.get('multi', False), resprint)
if view_type != 'tree':
resaction = filter(lambda x: not x.get('multi'), resaction)
resprint = filter(lambda x: not x.get('multi'), resprint)
resrelate = map(lambda x: x[2], resrelate)
for x in resprint + resaction + resrelate:
@ -3135,7 +3136,7 @@ class BaseModel(object):
if allfields and f not in allfields:
continue
res[f] = fields.field_to_dict(self, cr, user, context, field)
res[f] = fields.field_to_dict(self, cr, user, field, context=context)
if not write_access:
res[f]['readonly'] = True
@ -3469,7 +3470,7 @@ class BaseModel(object):
WHERE id IN %%s""" % self._table, (tuple(ids),))
uids = [x[0] for x in cr.fetchall()]
if len(uids) != 1 or uids[0] != uid:
raise orm.except_orm(_('AccessError'), '%s access is '
raise except_orm(_('AccessError'), '%s access is '
'restricted to your own records for transient models '
'(except for the super-user).' % operation.capitalize())
else:

View File

@ -39,7 +39,7 @@ except_osv = openerp.exceptions.Warning
service = None
class object_proxy():
class object_proxy(object):
def __init__(self):
self.logger = logging.getLogger('web-services')
global service
@ -118,8 +118,8 @@ class object_proxy():
if inst.name == 'AccessError':
self.logger.debug("AccessError", exc_info=True)
netsvc.abort_response(1, inst.name, 'warning', inst.value)
except except_osv, inst:
netsvc.abort_response(1, inst.name, 'warning', inst.value)
except except_osv:
raise
except IntegrityError, inst:
osv_pool = pooler.get_pool(dbname)
for key in osv_pool._sql_error.keys():

View File

@ -59,8 +59,7 @@ class TinySocketClientThread(threading.Thread):
while self.running:
try:
msg = ts.myreceive()
auth = getattr(self, 'auth_provider', None)
result = netsvc.dispatch_rpc(msg[0], msg[1], msg[2:], auth)
result = netsvc.dispatch_rpc(msg[0], msg[1], msg[2:])
ts.mysend(result)
except socket.timeout:
#terminate this channel because other endpoint is gone

View File

@ -144,17 +144,18 @@ def wsgi_jsonrpc(environ, start_response):
pass
def wsgi_webdav(environ, start_response):
if environ['REQUEST_METHOD'] == 'OPTIONS' and environ['PATH_INFO'] == '*':
pi = environ['PATH_INFO']
if environ['REQUEST_METHOD'] == 'OPTIONS' and pi in ['*','/']:
return return_options(environ, start_response)
http_dir = websrv_lib.find_http_service(environ['PATH_INFO'])
if http_dir:
path = environ['PATH_INFO'][len(http_dir.path):]
if path.startswith('/'):
environ['PATH_INFO'] = path
else:
environ['PATH_INFO'] = '/' + path
return http_to_wsgi(http_dir)(environ, start_response)
elif pi.startswith('/webdav'):
http_dir = websrv_lib.find_http_service(pi)
if http_dir:
path = pi[len(http_dir.path):]
if path.startswith('/'):
environ['PATH_INFO'] = path
else:
environ['PATH_INFO'] = '/' + path
return http_to_wsgi(http_dir)(environ, start_response)
def return_options(environ, start_response):
# Microsoft specific header, see