[MERGE] : with trunk

bzr revid: aja@tinyerp.com-20140220085105-7568yllve8ii0onl
This commit is contained in:
ajay javiya (OpenERP) 2014-02-20 14:21:05 +05:30
commit 905e34c788
31 changed files with 12469 additions and 173 deletions

View File

@ -588,7 +588,7 @@
<field name="partner_id" on_change="onchange_partner_id(partner_id)" domain="[
'&amp;',
'|',('parent_id','=',False),('is_company','=',True),
'|',('customer','=',True),('supplier','=',True)]"/>
'|',('customer','=',True),('supplier','=',True)]" context="{'default_supplier': 1}"/>
<field name="type" on_change="onchange_type(partner_id, type)"/>
<field name="account_id" options='{"no_open":True}' domain="[('journal_id','=',parent.journal_id), ('company_id', '=', parent.company_id)]"/>
<field name="analytic_account_id" groups="analytic.group_analytic_accounting" domain="[('company_id', '=', parent.company_id), ('type', '&lt;&gt;', 'view')]"/>

10849
addons/account/i18n/fr_CA.po Normal file

File diff suppressed because it is too large Load Diff

View File

@ -8,19 +8,19 @@ msgstr ""
"Project-Id-Version: openobject-addons\n"
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
"POT-Creation-Date: 2012-12-21 17:05+0000\n"
"PO-Revision-Date: 2010-09-29 11:28+0000\n"
"Last-Translator: OpenERP Administrators <Unknown>\n"
"PO-Revision-Date: 2014-02-18 16:35+0000\n"
"Last-Translator: Boško Stojaković <bluesoft83@gmail.com>\n"
"Language-Team: Bosnian <bs@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2014-01-28 06:28+0000\n"
"X-Generator: Launchpad (build 16914)\n"
"X-Launchpad-Export-Date: 2014-02-19 05:23+0000\n"
"X-Generator: Launchpad (build 16916)\n"
#. module: account_cancel
#: view:account.invoice:0
msgid "Cancel"
msgstr ""
msgstr "Otkaži"
#~ msgid "Account Cancel"
#~ msgstr "Računovodstvo - povrat"

View File

@ -8,14 +8,14 @@ msgstr ""
"Project-Id-Version: openobject-addons\n"
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
"POT-Creation-Date: 2012-12-21 17:05+0000\n"
"PO-Revision-Date: 2011-11-11 15:21+0000\n"
"Last-Translator: Fabien (Open ERP) <fp@tinyerp.com>\n"
"PO-Revision-Date: 2014-02-16 20:38+0000\n"
"Last-Translator: Harri Luuppala <Unknown>\n"
"Language-Team: Finnish <fi@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2014-01-28 05:51+0000\n"
"X-Generator: Launchpad (build 16914)\n"
"X-Launchpad-Export-Date: 2014-02-17 05:38+0000\n"
"X-Generator: Launchpad (build 16916)\n"
#. module: account_followup
#: model:email.template,subject:account_followup.email_template_account_followup_default
@ -55,12 +55,12 @@ msgstr ""
#: view:account_followup.followup.line:0
#: field:account_followup.followup.line,manual_action:0
msgid "Manual Action"
msgstr ""
msgstr "Manuaalinen toimenpide"
#. module: account_followup
#: field:account_followup.sending.results,needprinting:0
msgid "Needs Printing"
msgstr ""
msgstr "Odottaa tulostusta"
#. module: account_followup
#: view:res.partner:0

View File

@ -13,7 +13,7 @@
<record id="bank_swift_field" model="res.partner.bank.type.field">
<field name="name">bank_bic</field>
<field name="bank_type_id" ref="bank_iban"/>
<field eval="True" name="required"/>
<field eval="False" name="required"/>
<field eval="False" name="readonly"/>
</record>
<record id="bank_country_field" model="res.partner.bank.type.field">

View File

@ -0,0 +1,94 @@
# Finnish translation for openobject-addons
# Copyright (c) 2014 Rosetta Contributors and Canonical Ltd 2014
# This file is distributed under the same license as the openobject-addons package.
# FIRST AUTHOR <EMAIL@ADDRESS>, 2014.
#
msgid ""
msgstr ""
"Project-Id-Version: openobject-addons\n"
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
"POT-Creation-Date: 2012-12-21 17:05+0000\n"
"PO-Revision-Date: 2014-02-18 20:10+0000\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: Finnish <fi@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2014-02-19 05:23+0000\n"
"X-Generator: Launchpad (build 16916)\n"
#. module: event_sale
#: model:ir.model,name:event_sale.model_product_product
msgid "Product"
msgstr "Tuote"
#. module: event_sale
#: help:product.product,event_ok:0
msgid ""
"Determine if a product needs to create automatically an event registration "
"at the confirmation of a sales order line."
msgstr ""
#. module: event_sale
#: help:sale.order.line,event_id:0
msgid ""
"Choose an event and it will automatically create a registration for this "
"event."
msgstr ""
"Valitse tapahtuma ja se luo automaattisesti rekisteröinnin kyseiseen "
"tapahtumaan."
#. module: event_sale
#: model:event.event,name:event_sale.event_technical_training
msgid "Technical training in Grand-Rosiere"
msgstr ""
#. module: event_sale
#: help:product.product,event_type_id:0
msgid ""
"Select event types so when we use this product in sales order lines, it will "
"filter events of this type only."
msgstr ""
"Valitse tapahtumatyypit, joiden avulla myyntitilausrivillä voidaan suodattaa "
"vain tämän tyyppiset tapahtumat."
#. module: event_sale
#: field:product.product,event_type_id:0
msgid "Type of Event"
msgstr "Tapahtumatyyppi"
#. module: event_sale
#: field:sale.order.line,event_ok:0
msgid "event_ok"
msgstr ""
#. module: event_sale
#: field:product.product,event_ok:0
msgid "Event Subscription"
msgstr "Tapahtumaan rekisteröityminen"
#. module: event_sale
#: field:sale.order.line,event_type_id:0
msgid "Event Type"
msgstr "Tapahtumatyyppi"
#. module: event_sale
#: model:product.template,name:event_sale.event_product_product_template
msgid "Technical Training"
msgstr "Tekninen koulutus"
#. module: event_sale
#: code:addons/event_sale/event_sale.py:88
#, python-format
msgid "The registration %s has been created from the Sales Order %s."
msgstr "Rekisteröinti %s on luotu myyntitilaukselta %s."
#. module: event_sale
#: field:sale.order.line,event_id:0
msgid "Event"
msgstr "Tapahtuma"
#. module: event_sale
#: model:ir.model,name:event_sale.model_sale_order_line
msgid "Sales Order Line"
msgstr "Myyntitilausrivi"

View File

@ -62,19 +62,8 @@ class fleet_vehicle_cost(osv.Model):
res[record.id] = _('Unknown')
return res
def _cost_name_get_fnc(self, cr, uid, ids, name, unknow_none, context=None):
res = {}
for record in self.browse(cr, uid, ids, context=context):
name = record.vehicle_id.name
if record.cost_subtype_id.name:
name += ' / '+ record.cost_subtype_id.name
if record.date:
name += ' / '+ record.date
res[record.id] = name
return res
_columns = {
'name': fields.function(_cost_name_get_fnc, type="char", string='Name', store=True),
'name': fields.related('vehicle_id', 'name', type="char", string='Name', store=True),
'vehicle_id': fields.many2one('fleet.vehicle', 'Vehicle', required=True, help='Vehicle concerned by this log'),
'cost_subtype_id': fields.many2one('fleet.service.type', 'Type', help='Cost type purchased with this cost'),
'amount': fields.float('Total Price'),

View File

@ -832,6 +832,9 @@
</field>
</record>
<!--
fleet.vehicle.cost
-->
<record model='ir.actions.act_window' id='fleet_vehicle_service_types_act'>
<field name="name">Service Types</field>
<field name="res_model">fleet.service.type</field>
@ -848,6 +851,17 @@
<menuitem action="fleet_vehicle_service_types_act" parent="fleet_configuration" id="fleet_vehicle_service_types_menu" groups="base.group_no_one"/>
<record model='ir.ui.view' id='fleet_vehicle_cost_tree'>
<field name="name">fleet.vehicle.cost.tree</field>
<field name="model">fleet.vehicle.cost</field>
<field name="arch" type="xml">
<tree string="Vehicle Costs">
<field name="vehicle_id"/>
<field name="cost_subtype_id"/>
<field name="date"/>
</tree>
</field>
</record>
<record model='ir.ui.view' id='fleet_vehicle_costs_report'>
<field name="name">fleet.vehicle.cost.graph</field>
@ -939,31 +953,5 @@
</record>
<menuitem action="fleet_vehicle_costs_act" parent="fleet_vehicles" id="fleet_vehicle_costs_menu" groups="group_fleet_manager"/>
<!--
<record model='ir.ui.view' id='fleet_hr_employee_form'>
<field name="name">fleet.hr.employee.form</field>
<field name="model">hr.employee</field>
<field name="type">form</field>
<field name="inherit_id" ref="hr.view_employee_form" />
<field name="arch" type="xml">
<notebook position="inside">
<page string="Vehicle">
<group>
<field name="vehicle_id" widget="many2many_tags"/>
</group>
</page>
</notebook>
</field>
</record>
<record model="fleet.vehicle.model" id="citroen">
<field name="name">Citroen</field>
</record>
<record model="fleet.vehicle" id="stw_vehicle">
<field name="name">240BTN</field>
<field name="model_id" ref="citroen" />
</record>
-->
</data>
</openerp>

View File

@ -21,6 +21,7 @@
import logging
from openerp import SUPERUSER_ID
from openerp import tools
from openerp.modules.module import get_module_resource
from openerp.osv import fields, osv
@ -248,27 +249,46 @@ class hr_employee(osv.osv):
'color': 0,
}
def create(self, cr, uid, data, context=None):
if context is None:
context = {}
create_ctx = dict(context, mail_create_nolog=True)
employee_id = super(hr_employee, self).create(cr, uid, data, context=create_ctx)
def _broadcast_welcome(self, cr, uid, employee_id, context=None):
""" Broadcast the welcome message to all users in the employee company. """
employee = self.browse(cr, uid, employee_id, context=context)
partner_ids = []
_model, group_id = self.pool['ir.model.data'].get_object_reference(cr, uid, 'base', 'group_user')
if employee.user_id:
res_users = self.pool['res.users']
# send a copy to every user of the company
# TODO: post to the `Whole Company` mail.group when we'll be able to link to the employee record
_model, group_id = self.pool['ir.model.data'].get_object_reference(cr, uid, 'base', 'group_user')
user_ids = res_users.search(cr, uid, [('company_id', '=', employee.user_id.company_id.id),
('groups_id', 'in', group_id)])
partner_ids = list(set(u.partner_id.id for u in res_users.browse(cr, uid, user_ids, context=context)))
company_id = employee.user_id.company_id.id
elif employee.company_id:
company_id = employee.company_id.id
elif employee.job_id:
company_id = employee.job_id.company_id.id
elif employee.department_id:
company_id = employee.department_id.company_id.id
else:
partner_ids = []
self.message_post(cr, uid, [employee_id],
company_id = self.pool['res.company']._company_default_get(cr, uid, 'hr.employee', context=context)
res_users = self.pool['res.users']
user_ids = res_users.search(
cr, SUPERUSER_ID, [
('company_id', '=', company_id),
('groups_id', 'in', group_id)
], context=context)
partner_ids = list(set(u.partner_id.id for u in res_users.browse(cr, SUPERUSER_ID, user_ids, context=context)))
self.message_post(
cr, uid, [employee_id],
body=_('Welcome to %s! Please help him/her take the first steps with OpenERP!') % (employee.name),
partner_ids=partner_ids,
subtype='mail.mt_comment', context=context
)
return True
def create(self, cr, uid, data, context=None):
if context is None:
context = {}
if context.get("mail_broadcast"):
context['mail_create_nolog'] = True
employee_id = super(hr_employee, self).create(cr, uid, data, context=context)
if context.get("mail_broadcast"):
self._broadcast_welcome(cr, uid, employee_id, context=context)
return employee_id
def unlink(self, cr, uid, ids, context=None):

View File

@ -453,6 +453,7 @@ class hr_applicant(osv.Model):
contact_name = self.pool.get('res.partner').name_get(cr, uid, [applicant.partner_id.id])[0][1]
if applicant.job_id and (applicant.partner_name or contact_name):
applicant.job_id.write({'no_of_hired_employee': applicant.job_id.no_of_hired_employee + 1}, context=context)
create_ctx = dict(context, mail_broadcast=True)
emp_id = hr_employee.create(cr, uid, {'name': applicant.partner_name or contact_name,
'job_id': applicant.job_id.id,
'address_home_id': address_id,
@ -460,7 +461,7 @@ class hr_applicant(osv.Model):
'address_id': applicant.company_id and applicant.company_id.partner_id and applicant.company_id.partner_id.id or False,
'work_email': applicant.department_id and applicant.department_id.company_id and applicant.department_id.company_id.email or False,
'work_phone': applicant.department_id and applicant.department_id.company_id and applicant.department_id.company_id.phone or False,
})
}, context=create_ctx)
self.write(cr, uid, [applicant.id], {'emp_id': emp_id}, context=context)
self.pool['hr.job'].message_post(
cr, uid, [applicant.job_id.id],

Binary file not shown.

After

Width:  |  Height:  |  Size: 66 KiB

View File

@ -0,0 +1,548 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="1600px"
height="1200px"
id="svg2985"
version="1.1"
inkscape:version="0.48.3.1 r9886"
sodipodi:docname="posbox_doc_schema.svg"
inkscape:export-filename="/home/fva/Code/openerp/posbox_doc_schema.png"
inkscape:export-xdpi="67.5"
inkscape:export-ydpi="67.5">
<defs
id="defs2987">
<marker
inkscape:stockid="DotL"
orient="auto"
refY="0.0"
refX="0.0"
id="DotL"
style="overflow:visible">
<path
id="path6730"
d="M -2.5,-1.0 C -2.5,1.7600000 -4.7400000,4.0 -7.5,4.0 C -10.260000,4.0 -12.5,1.7600000 -12.5,-1.0 C -12.5,-3.7600000 -10.260000,-6.0 -7.5,-6.0 C -4.7400000,-6.0 -2.5,-3.7600000 -2.5,-1.0 z "
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt"
transform="scale(0.8) translate(7.4, 1)" />
</marker>
<marker
inkscape:stockid="DotM"
orient="auto"
refY="0.0"
refX="0.0"
id="DotM"
style="overflow:visible">
<path
id="path6733"
d="M -2.5,-1.0 C -2.5,1.7600000 -4.7400000,4.0 -7.5,4.0 C -10.260000,4.0 -12.5,1.7600000 -12.5,-1.0 C -12.5,-3.7600000 -10.260000,-6.0 -7.5,-6.0 C -4.7400000,-6.0 -2.5,-3.7600000 -2.5,-1.0 z "
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt"
transform="scale(0.4) translate(7.4, 1)" />
</marker>
<pattern
inkscape:collect="always"
xlink:href="#Strips1_3"
id="pattern6512"
patternTransform="matrix(1.4070053,-1.4070053,10.196067,10.196067,0,0)" />
<pattern
inkscape:stockid="Stripes 1:3"
id="Strips1_3"
patternTransform="translate(0,0) scale(10,10)"
height="1"
width="4"
patternUnits="userSpaceOnUse"
inkscape:collect="always">
<rect
id="rect4622"
height="2"
width="1"
y="-0.5"
x="0"
style="fill:black;stroke:none" />
</pattern>
</defs>
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="1"
inkscape:pageshadow="2"
inkscape:zoom="0.45254834"
inkscape:cx="679.01909"
inkscape:cy="813.9637"
inkscape:current-layer="layer1"
inkscape:document-units="px"
showgrid="false"
inkscape:window-width="1920"
inkscape:window-height="991"
inkscape:window-x="0"
inkscape:window-y="27"
inkscape:window-maximized="1" />
<metadata
id="metadata2990">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
id="layer1"
inkscape:label="Layer 1"
inkscape:groupmode="layer">
<g
id="g7313">
<g
transform="translate(0,35.355339)"
id="g6566">
<g
id="g6514"
transform="translate(-10.9375,-57.8125)">
<path
inkscape:connector-curvature="0"
id="path6489"
d="m 905,179.59375 -34.8125,31.34375 -118.78125,0 c -5.54,0 -10,4.46 -10,10 l 0,102.5 -157.5,0 c -16.62,0 -30,13.38 -30,30 l 0,632.3125 -27.4375,24.9375 33.25,44.2813 c 0.10609,0.1442 0.2039,0.2952 0.3125,0.4374 l 2.125,2.8126 0.21875,-0.125 c 5.44486,5.6076 13.06148,9.0937 21.53125,9.0937 l 463.43755,0 c 16.6199,0 30,-13.38 30,-30 l 0,-683.75 c 0,-10.90688 -5.7475,-20.40588 -14.4063,-25.65625 l -41.125,-31 -27.3125,26.65625 -45.28125,0 0,-102.5 c 0,-2.89877 -1.22955,-5.48931 -3.1875,-7.3125 l 0.25,-0.375 L 905,179.59375 z"
style="opacity:0.25;fill:url(#pattern6512);fill-opacity:1;stroke:none" />
<g
transform="translate(-2.2097087,75.130096)"
id="g3823">
<g
id="g3847">
<rect
ry="5.274591"
y="106.16312"
x="711.8349"
height="151.06096"
width="194.27489"
id="rect3843"
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:8.48901749;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
rx="5.274591" />
<rect
rx="5.274591"
style="fill:none;stroke:#000000;stroke-width:2;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="rect3845"
width="175.41872"
height="151.06096"
x="721.263"
y="106.16312"
ry="5.274591" />
</g>
<rect
rx="5.274591"
ry="5.274591"
y="869.83844"
x="746.01172"
height="110.99157"
width="131.81378"
id="rect3765"
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:8.48901749;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<rect
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:8.48901749;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="rect6618"
width="125.18465"
height="53.539146"
x="938.25635"
y="571.52777"
ry="5.274591"
rx="5.274591" />
<rect
rx="34.723557"
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:8;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="rect2993"
width="509.11688"
height="730.677"
x="525.61603"
y="217.12157"
ry="34.723557" />
<rect
rx="21.787001"
ry="21.787001"
y="235.37366"
x="543.0672"
height="694.12708"
width="474.21454"
id="rect3763"
style="fill:none;stroke:#000000;stroke-width:1.99425566;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<rect
style="fill:none;stroke:#000000;stroke-width:1.99425554;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="rect3767"
width="160.64433"
height="9.1270761"
x="562.84052"
y="740.37366"
rx="5.3000002"
ry="5.3000002" />
<rect
ry="5.3000002"
rx="5.2999997"
y="667.30597"
x="828.00549"
height="9.1270761"
width="73.434502"
id="rect3769"
style="fill:none;stroke:#000000;stroke-width:1.99399996;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<rect
ry="5.3000002"
rx="5.3000002"
y="313.75256"
x="693.65527"
height="9.1270761"
width="160.64433"
id="rect3771"
style="fill:none;stroke:#000000;stroke-width:1.99425554;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<g
id="g3783">
<rect
ry="5.3000002"
rx="5.3000002"
y="245.39903"
x="962.35583"
height="271.93509"
width="43.971706"
id="rect3773"
style="fill:none;stroke:#000000;stroke-width:1.99425554;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<rect
ry="5.3000002"
rx="5.3000002"
y="374.20874"
x="952.03491"
height="7.0710678"
width="21.213203"
id="rect3775"
style="fill:#ffffff;fill-opacity:1;stroke:none" />
<rect
style="fill:#ffffff;fill-opacity:1;stroke:none"
id="rect3777"
width="21.213203"
height="7.0710678"
x="992.86823"
y="373.3754"
rx="5.3000002"
ry="5.3000002" />
<rect
transform="matrix(0,-1,1,0,0,0)"
ry="5.3000002"
rx="5.3000002"
y="981.60596"
x="-260.01752"
height="7.0710678"
width="21.213203"
id="rect3779"
style="fill:#ffffff;fill-opacity:1;stroke:none" />
<rect
style="fill:#ffffff;fill-opacity:1;stroke:none"
id="rect3781"
width="21.213203"
height="7.0710678"
x="-526.6842"
y="981.60596"
rx="5.3000002"
ry="5.3000002"
transform="matrix(0,-1,1,0,0,0)" />
</g>
<path
inkscape:connector-curvature="0"
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:2;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
d="m 958.1875,822.25 c -9.01707,3.59482 -15.375,12.41301 -15.375,22.71875 0,13.50563 10.93187,24.46875 24.4375,24.46875 13.50563,0 24.46875,-10.96312 24.46875,-24.46875 0,-10.17788 -6.2141,-18.91637 -15.0625,-22.59375 l 0,8.8125 c 4.63325,2.9517 7.6875,8.02222 7.6875,13.78125 0,9.11223 -7.65608,16.5 -17.09375,16.5 -9.43767,0 -17.0625,-7.38777 -17.0625,-16.5 0,-5.88681 3.20248,-11.04837 8,-13.96875 l 0,-8.75 z"
id="path3792" />
<g
id="g3818"
transform="translate(0,-1.767767)">
<rect
ry="5.3000002"
rx="5.2999992"
y="879.66095"
x="943.13324"
height="8.7558908"
width="46.827415"
id="rect3794"
style="fill:none;stroke:#000000;stroke-width:1.99399996;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
<rect
style="fill:none;stroke:#000000;stroke-width:1.99399996;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="rect3798"
width="46.827415"
height="8.7558908"
x="943.13324"
y="895.68982"
rx="5.2999992"
ry="5.3000002" />
<rect
ry="5.3000002"
rx="5.2999992"
y="910.22754"
x="943.13324"
height="8.7558908"
width="46.827415"
id="rect3800"
style="fill:none;stroke:#000000;stroke-width:1.99399996;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
</g>
<rect
ry="5.3000002"
rx="5.2999992"
y="963.05292"
x="-845.58075"
height="8.7558908"
width="32.390652"
id="rect3812"
style="fill:#ffffff;fill-opacity:1;stroke:#000000;stroke-width:1.99400008;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
transform="matrix(0,-1,1,0,0,0)" />
</g>
</g>
<g
id="g6559"
transform="translate(0,-7.7339804)">
<path
transform="matrix(1,0,0,0.85333333,0,117.03125)"
d="m 1119.5313,856.64062 c 0,5.82488 -4.1974,10.54688 -9.375,10.54688 -5.1777,0 -9.375,-4.722 -9.375,-10.54688 0,-5.82487 4.1973,-10.54687 9.375,-10.54687 5.1776,0 9.375,4.722 9.375,10.54687 z"
sodipodi:ry="10.546875"
sodipodi:rx="9.375"
sodipodi:cy="856.64062"
sodipodi:cx="1110.1562"
id="path6539"
style="fill:#00fd28;fill-opacity:1;stroke:#000000;stroke-width:2.16506362;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
sodipodi:type="arc" />
<path
sodipodi:type="arc"
style="fill:#ff0d0d;fill-opacity:1;stroke:#000000;stroke-width:2.16506362;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="path6541"
sodipodi:cx="1110.1562"
sodipodi:cy="856.64062"
sodipodi:rx="9.375"
sodipodi:ry="10.546875"
d="m 1119.5313,856.64062 c 0,5.82488 -4.1974,10.54688 -9.375,10.54688 -5.1777,0 -9.375,-4.722 -9.375,-10.54688 0,-5.82487 4.1973,-10.54687 9.375,-10.54687 5.1776,0 9.375,4.722 9.375,10.54687 z"
transform="matrix(1,0,0,0.85333333,0,141.44531)" />
<path
transform="matrix(1,0,0,0.85333333,0,165.85937)"
d="m 1119.5313,856.64062 c 0,5.82488 -4.1974,10.54688 -9.375,10.54688 -5.1777,0 -9.375,-4.722 -9.375,-10.54688 0,-5.82487 4.1973,-10.54687 9.375,-10.54687 5.1776,0 9.375,4.722 9.375,10.54687 z"
sodipodi:ry="10.546875"
sodipodi:rx="9.375"
sodipodi:cy="856.64062"
sodipodi:cx="1110.1562"
id="path6543"
style="fill:#00fd28;fill-opacity:1;stroke:#000000;stroke-width:2.16506362;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
sodipodi:type="arc" />
<path
sodipodi:type="arc"
style="fill:#00fd28;fill-opacity:1;stroke:#000000;stroke-width:2.16506362;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
id="path6545"
sodipodi:cx="1110.1562"
sodipodi:cy="856.64062"
sodipodi:rx="9.375"
sodipodi:ry="10.546875"
d="m 1119.5313,856.64062 c 0,5.82488 -4.1974,10.54688 -9.375,10.54688 -5.1777,0 -9.375,-4.722 -9.375,-10.54688 0,-5.82487 4.1973,-10.54687 9.375,-10.54687 5.1776,0 9.375,4.722 9.375,10.54687 z"
transform="matrix(1,0,0,0.85333333,0,190.27344)" />
<path
transform="matrix(1,0,0,0.85333333,0,214.6875)"
d="m 1119.5313,856.64062 c 0,5.82488 -4.1974,10.54688 -9.375,10.54688 -5.1777,0 -9.375,-4.722 -9.375,-10.54688 0,-5.82487 4.1973,-10.54687 9.375,-10.54687 5.1776,0 9.375,4.722 9.375,10.54687 z"
sodipodi:ry="10.546875"
sodipodi:rx="9.375"
sodipodi:cy="856.64062"
sodipodi:cx="1110.1562"
id="path6547"
style="fill:#fff90d;fill-opacity:1;stroke:#000000;stroke-width:2.16506362;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
sodipodi:type="arc" />
</g>
</g>
<text
sodipodi:linespacing="125%"
id="text6598"
y="178.8759"
x="514.01447"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="178.8759"
x="514.01447"
id="tspan6600"
sodipodi:role="line">2A Power</tspan></text>
<text
xml:space="preserve"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
x="724.2699"
y="127.21583"
id="text6602"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan6604"
x="724.2699"
y="127.21583"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans">SD Card</tspan></text>
<text
sodipodi:linespacing="125%"
id="text6606"
y="626.60999"
x="319.89322"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="626.60999"
x="319.89322"
id="tspan6608"
sodipodi:role="line">HDMI</tspan></text>
<text
xml:space="preserve"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
x="761.83496"
y="1097.278"
id="text6610"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan6612"
x="761.83496"
y="1097.278"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans">USB</tspan></text>
<text
sodipodi:linespacing="125%"
id="text6614"
y="1097.278"
x="596.10681"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="1097.278"
x="596.10681"
id="tspan6616"
sodipodi:role="line">RJ45</tspan></text>
<text
xml:space="preserve"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
x="1135.8894"
y="660.90717"
id="text6620"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan6622"
x="1135.8894"
y="660.90717"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans">Composite</tspan></text>
<text
sodipodi:linespacing="125%"
id="text6624"
y="774.18842"
x="1135.8894"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="774.18842"
x="1135.8894"
id="tspan6626"
sodipodi:role="line">Audio</tspan></text>
<text
xml:space="preserve"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
x="1135.8894"
y="774.18842"
id="text6628"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan6630"
x="1135.8894"
y="774.18842"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans">Audio</tspan></text>
<text
sodipodi:linespacing="125%"
id="text6632"
y="891.37592"
x="1212.4519"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="891.37592"
x="1212.4519"
id="tspan6634"
sodipodi:role="line">Ready</tspan></text>
<text
xml:space="preserve"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
x="1212.4519"
y="940.45667"
id="text6636"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan6638"
x="1212.4519"
y="940.45667"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans">Power</tspan></text>
<text
sodipodi:linespacing="125%"
id="text6640"
y="986.97278"
x="1212.4519"
style="font-size:36.98903275px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-family:Droid Sans;-inkscape-font-specification:Droid Sans"
y="986.97278"
x="1212.4519"
id="tspan6642"
sodipodi:role="line">Network</tspan></text>
<path
inkscape:connector-curvature="0"
id="path6663"
d="m 437.5,614.15728 54.6875,0"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)" />
<path
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 601.86625,199.79103 0,54.6875"
id="path7295"
inkscape:connector-curvature="0" />
<path
inkscape:connector-curvature="0"
id="path7297"
d="m 1113.1075,650.87603 -54.6875,0"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)" />
<path
sodipodi:nodetypes="cc"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 1113.1075,761.81353 -76.5625,0"
id="path7299"
inkscape:connector-curvature="0" />
<path
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 1192.657,876.26632 -54.6875,0"
id="path7301"
inkscape:connector-curvature="0" />
<path
sodipodi:nodetypes="cc"
inkscape:connector-curvature="0"
id="path7303"
d="m 1192.657,927.08963 -54.6875,-27.62136"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)" />
<path
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 1192.657,974.04593 -54.6875,0"
id="path7305"
inkscape:connector-curvature="0" />
<path
sodipodi:nodetypes="cc"
inkscape:connector-curvature="0"
id="path7307"
d="m 1192.657,974.04593 -54.6875,-24.85922"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)" />
<path
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 1192.657,974.04593 -54.6875,-49.16602"
id="path7309"
inkscape:connector-curvature="0"
sodipodi:nodetypes="cc" />
<path
sodipodi:nodetypes="cc"
style="fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;marker-start:url(#DotL)"
d="m 630.03792,1053.883 0,-32.0313"
id="path7311"
inkscape:connector-curvature="0" />
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 24 KiB

View File

@ -0,0 +1,395 @@
====================
PosBox Documentation
====================
Posbox Setup Guide
==================
Prerequisites
-------------
Before you start setting up your PosPox make sure you have everything.
You will need :
- The PosBox
- A 2A Power adapter
- A computer or tablet with an up to date Firefox, Chrome or Safari web
browser (we recommend Chrome)
- A running SaaS or V8.0 OpenERP Instance with the Point of Sale
Installed.
- A local network set up with DHCP ( this is the default setting )
- A RJ45 Ethrnet Cable
- An Epson USB TM-T20 Printer or another compatible printer.
- A Honewell Voyager USB Barcode Scanner or another compatible scanner.
- An Epson compatible cash drawer.
Setup
-----
.. image:: _images/posbox_doc_schema.png
:width: 100%
:align: center
1) Power the PosBox.
~~~~~~~~~~~~~~~~~~~~
Plug the PosBox to the 2A Power Adapter, a bright red status led should
light up.
2) Connect it to the Local Network
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Connect the PosBox to the Local Network with the RJ45 Cable. Make sure
You connect the PosBox to the same Network as your POS device. Once
connected a bright yellow status led should light up, and a green status
led should flash.
3) Connect the USB Printer
~~~~~~~~~~~~~~~~~~~~~~~~~~
Put a paper roll in the printer, power it up, then connect it to one of
the PosBox's USB port
4) Connect the cash drawer
~~~~~~~~~~~~~~~~~~~~~~~~~~
The cash drawer should be connected to the printer with the RJ25 cable
5) Connect the USB Barcode Scanner
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Connect the usb barcode scanner to one of the PosBox's USB port. The
Barcode Scanner should immediately light up and emit a loud beep.
6) Configure the USB Barcode Scanner
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The barcode scanner should be configured in QWERTY and emit a new line /
return symbol after each scan. This is most likely the default
configuration of your barcode scanner.
7) Make sure the PosBox is ready
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Once powered, The PosBox needs less than a minute to boot. Once the
PosBox is ready, it should print a status receipt with its IP Adress.
Also, the last status led, just after the red power status led, should
be permanently lit green.
8) Set up the Point of Sale
~~~~~~~~~~~~~~~~~~~~~~~~~~~
Make sure to activate the 'Print via Proxy', 'Remote Scanning' or
'Cashdrawer' options in the Point of Sale configuration. If you are
using firefox, you must manually specify the PosBox's IP address which
was printed on the status receipt.
If you are running multiple Point of Sales on the same PosBox, make sure
that only one of them has Remote Scanning activated.
9) Launch the Point of Sale.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
If you didn't spcecify the PosBox's IP address in the config, the POS
will need some time to perform a network scan to find the PosBox. This
is only done once.
The Point of Sale is now connected to the PosBox and your Hardware
should be ready to use.
PosBoxless Setup Guide
======================
If you are running your Point of Sale on a debian-based linux
distribution, you do not need the PosBox as you can run its software
locally. However the installation process is not foolproof. You'll need
at least to know how to install and run openerp. You may also run into
issues specific to your distribution or to your particular setup and
hardware configuration.
Prerequisites
-------------
- A debian based linux distribution (Debian, Ubuntu, Mint, etc.)
- A running trunk version of the OpenERP server
- You must uninstall any esc-pos printer driver as it will conflict
with OpenERP's built-in driver.
Setup
-----
1) Extra dependencies
~~~~~~~~~~~~~~~~~~~~~
The driver modules requires the installation of new python modules:
::
$ sudo pip install pyserial
$ sudo pip install --pre pyusb
2) Database Setup
~~~~~~~~~~~~~~~~~
You must create a database called ``posbox`` with the modules
``hw_proxy``, ``hw_escpos``, and ``hw_scanner`` installed.
3) Access Rights
~~~~~~~~~~~~~~~~
The drivers need raw access to the printer and barcode scanner devices.
Doing so requires a bit system administration. First we are going to
create a group that has haccess to usb devices:
::
$ sudo groupadd usbusers
Then we add the user who will run the OpenERP server to ``usbusers``
::
$ sudo useradd -G usbusers USERNAME
Then we need to create a udev rule that will automatically allow members
of ``usbusers`` to access raw usb devices. To do so create a file called
``99-usbusers.rule`` in the ``/etc/udev/rules.d/`` directory with the
following content:
::
SUBSYSTEM=="usb", GROUP="usbusers", MODE="0660"
SUBSYSTEMS=="usb", GROUP="usbusers", MODE="0660"
Then you need to reboot your machine.
4) Start the local OpenERP Installl
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
We must launch the OpenERP server on the port ``8069`` with the correct
database settings:
::
$ ./server/openerp-server --addons-path=addons,web/addons --db-filter='^posbox$' \
--xmlrpc-port=8069 -d posbox
5) Check that everything works
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Plug all your hardware to your machine's USB ports, and go to
``http://localhost/hw_proxy/status`` refresh the page a few times and
see if all your devices are indicated as *Connected*. Possible source of
errors are: The paths on the distribution differ from the paths expected
by the drivers, another process has grabbed exclusive access to the
devices, the udev rules do not apply or a superceeded by others.
5) Automatically Start OpenERP
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
You must now make sure that this OpenERP install is automatically
started after boot. There are various ways to do so, and how to do it
depends on your particular setup. We use *systemd* on the PosBox, but
*upstart* or *sysvinit* are other options.
6) Set up the Point of Sale
~~~~~~~~~~~~~~~~~~~~~~~~~~~
Make sure that one of the posbox Make sure the IP Adress field in the
POS Config is either ``127.0.0.1`` or ``localhost`` or simply leave it
empty.
PosBox Technical Documentation
==============================
Technical Overview
------------------
The PosBox Hardware
~~~~~~~~~~~~~~~~~~~
The PosBox's Hardware is based on a model B Raspberry Pi, a popular
open-source micro-computer. The Raspberry Pi is powered with a 2A
micro-usb power adapter. 2A is needed to give enough power to the
barcode scanners. And we recommend Samsung power adapters for their
availability and reliability ( but beware of counterfeits ). The
Raspberry is protected by a ModMyPi Raspberry Pi Case. The Software is
installed on a 8Gb Class 10 or Higher SD Card. The SD Card's class is
important to ensure good performances. All this hardware is easily
available worldwide from independant vendors.
Compatible Peripherals
~~~~~~~~~~~~~~~~~~~~~~
- Printers:
- Epson TM-T20
- Support for Other Esc-Pos compatible printers can be easily added
on a case-by-case basis, please see the *Unsupported Printers*
chapter of this manual.
- Barcode Scannners:
- Metapace S61
- Honeywell Voyager 95x0 Series.
- Most other barcode scanners should work out of the box. Some
barcode scanners need more power than the PosBox can provide and
must be plugged in a self-powered USB HUB. This is the case for
Datalogic Barcode Scanners.
- Cash Drawers:
- As the cash drawers are connected to the printer, All Epson
compatible cash drawers should work out of the Box.
The PosBox Software
~~~~~~~~~~~~~~~~~~~
The PosBox runs a Raspbian Linux distribution, a Debian derivative
optimized for the Raspberry Pi. It also runs a barebones install of
OpenERP which provides the webserver and the drivers. The printer &
scanner drivers are implemented as openerp modules. Those modules are
named ``hw_proxy``, ``hw_escpos``, ``hw_scanner`` and are the only
modules installed and running. OpenERP is only used for the framework it
provides. No business data is processed or stored on the PosBox. The
OpenERP install is a full bazaar clone of the ``trunk`` branch, and can
thus be updated trough the usual means.
We use systemd to manage the Openerp server. Systemd makes sure OpenERP
starts up at boot and is always up and running. Its systemd unit file is
called ``openerp.service``, and can be found in
``/etc/systemd/system/openerp.service``. The systemd version used is
quite old and thus ``journalctl`` is not available. All logs can be
found in instead ``/var/logs/syslog``
We removed all graphical software from the default install to reduce to
image size but nothing prevents you from reinstalling them.
Local Access
~~~~~~~~~~~~
If you plug a QWERTY USB keyboard into one of the PosBox's USB ports,
and if you connect a computer monitor to the *HDMI* port of the PosBox,
you can use it as a small UNIX computer and perform various
administration tasks.
Once the PosBox is ready press ``ALT-F2`` to access the login prompt.
The login is ``pi`` and the password ``admin``. The OpenERP install is
in the ``~/openerp`` directory along with a few scripts to help with
debugging and administration.
Remote Access
~~~~~~~~~~~~~
If you have the PosBox's IP address and a SSH client you can access the
PosBox's system remotely. The login / password are ``pi``/``admin``
Unsupported Printers
~~~~~~~~~~~~~~~~~~~~
The PosBox should be able to print to any ESC-POS printer, not just the
Epson TM-T20. If You have such a printer, you can activate it with the
following steps:
- Get local or remote access to the PosBox.
- Plug in your printer
- type ``lsusb`` in a prompt
- Find your printer in the list of connected USB devices
- Find your printer's vendor id: It consists of two hexadecimal numbers
separated by a colon.
- Edit ``~/openerp/addons/hw_escpos/escpos/supported_devices.py`` and
add an entry for your printer.
- Restar The PosBox.
- If everything works properly you can send your printer's name and
vendor ID to ``support@openerp.com`` and we'll add it to the list of
supported devices.
Updating The PosBox Software
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The best way to update the PosBox software is to download a new version
of the image and flash the SD-Card with it. This operation is described
in details on the following tutorial
``http://elinux.org/RPi_Easy_SD_Card_Setup``, just replace the standard
raspberry pi image to the latest one found at
``http://nightly.openerp.com/trunk/posbox/``
Troubleshoot
------------
The POS cannot connect to the PosBox.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- The easiest way to make sure the PosBox is properly set-up is to turn
it on with the printer plugged in as it will print a receipt
indicating any error if encountered or the PosBox's IP adress in case
of success. If no receipt is printed, check the following steps:
- Make sure the PosBox is powered on, indicated by a brightly lid red
status LED.
- Make sure the PosBox is ready, this is indicated by a brightly lid
green status LED just above the red power status LED. The PosBox
should be ready one minute after it is powered on.
- Make sure the PosBox is connected to the Network. This is indicated
by a brightly lid yellow status LED.
- Make sure the PosBox is connected to the same network as your POS
device. Both the device and the posbox should be visible in the list
of connected devices on your network router.
- Make sure that your LAN is set up with DHCP, and gives ip Address in
the range 192.168.0.X, 192.168.1.X, 10.0.0.X. If you cannot setup
your LAN that way, you must manually set up your PosBox's ip-address.
See the relevant paragraph in the Setup chapter of this documentation
- If you have specified the PosBox's IP address in the config, make
sure it correspond to the printed on the PosBox's status receipt.
- Make sure that the POS is not loaded over HTTPS.
- A bug in Firefox's HTTP implementation prevents the autodiscovery
from working reliably. When using Firefox you should manually set up
the PosBox's ip address in the POS config.
The Barcode Scanner is not working
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- The PosBox needs a 2A power supply to work with some barcode
scanners. If you are not using the provided power supply, make sure
the one you use has enough power.
- Some barcode scanners will need more than 2A and will not work, or
will work unreliably, even with the provided power supply. In those
case you can plug the barcode scanner in a self-powered USB Hub.
- Some poorly built barcode scanners do not advertise themselves as
barcode scanners but as a usb keyboard instead, and will not be
recognized by the PosBox.
The Barcode Scanner is not working reliably
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- Make sure that no more than one device with 'Scan via Proxy' enabled
are connected to the PosBox at the same time.
Printing the receipt takes too much time.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- A small delay before the first print is expected, as the PosBox will
do some preprocessing to speed up the next printings. If you suffer
delays afterwards it is most likely due to poor network connection
between the POS and the PosBox.
Some characters are not correctly printed on the receipt.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- The PosBox does not support all languages and characters. It
currently supports latin and cyrillic based scripts, with basic
japanese support.
The Printer is Offline
~~~~~~~~~~~~~~~~~~~~~~
- The PosBox only supports EPSON TM-T20 printers. Make sure the printer
is connected, powered, has enough paper and has its lid closed, and
does is not in an error status. If the error persists, please contact
support.
The Cashdrawer does not open.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- The cashdrawer should be connected to the printer and should be
activated in the POS Configuration

View File

@ -348,11 +348,7 @@ class mail_thread(osv.AbstractModel):
message_follower_ids = values.get('message_follower_ids') or [] # webclient can send None or False
message_follower_ids.append([4, pid])
values['message_follower_ids'] = message_follower_ids
# add operation to ignore access rule checking for subscription
context_operation = dict(context, operation='create')
else:
context_operation = context
thread_id = super(mail_thread, self).create(cr, uid, values, context=context_operation)
thread_id = super(mail_thread, self).create(cr, uid, values, context=context)
# automatic logging unless asked not to (mainly for various testing purpose)
if not context.get('mail_create_nolog'):
@ -1558,12 +1554,11 @@ class mail_thread(osv.AbstractModel):
user_pid = self.pool.get('res.users').browse(cr, uid, uid, context=context).partner_id.id
if set(partner_ids) == set([user_pid]):
if context.get('operation', '') != 'create':
try:
self.check_access_rights(cr, uid, 'read')
self.check_access_rule(cr, uid, ids, 'read')
except (osv.except_osv, orm.except_orm):
return False
try:
self.check_access_rights(cr, uid, 'read')
self.check_access_rule(cr, uid, ids, 'read')
except (osv.except_osv, orm.except_orm):
return False
else:
self.check_access_rights(cr, uid, 'write')
self.check_access_rule(cr, uid, ids, 'write')

286
addons/note/i18n/fi.po Normal file
View File

@ -0,0 +1,286 @@
# Finnish translation for openobject-addons
# Copyright (c) 2014 Rosetta Contributors and Canonical Ltd 2014
# This file is distributed under the same license as the openobject-addons package.
# FIRST AUTHOR <EMAIL@ADDRESS>, 2014.
#
msgid ""
msgstr ""
"Project-Id-Version: openobject-addons\n"
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
"POT-Creation-Date: 2012-12-21 17:04+0000\n"
"PO-Revision-Date: 2014-02-18 16:05+0000\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: Finnish <fi@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2014-02-19 05:23+0000\n"
"X-Generator: Launchpad (build 16916)\n"
#. module: note
#: field:note.note,memo:0
msgid "Note Content"
msgstr "Muistiinpanon sisältö"
#. module: note
#: view:note.stage:0
msgid "Stages of Notes"
msgstr "Muistiipanojen vaiheet"
#. module: note
#: model:note.stage,name:note.demo_note_stage_04
#: model:note.stage,name:note.note_stage_02
msgid "This Week"
msgstr "Tämä viikko"
#. module: note
#: model:ir.model,name:note.model_base_config_settings
msgid "base.config.settings"
msgstr ""
#. module: note
#: model:ir.model,name:note.model_note_tag
msgid "Note Tag"
msgstr "Muistiinpanon tunniste"
#. module: note
#: model:res.groups,name:note.group_note_fancy
msgid "Notes / Fancy mode"
msgstr ""
#. module: note
#: model:ir.model,name:note.model_note_note
#: view:note.note:0
msgid "Note"
msgstr "Muistiinpano"
#. module: note
#: view:note.note:0
msgid "Group By..."
msgstr "Ryhmittely..."
#. module: note
#: field:note.note,message_follower_ids:0
msgid "Followers"
msgstr "Seuraajat"
#. module: note
#: model:ir.actions.act_window,help:note.action_note_note
msgid ""
"<p class=\"oe_view_nocontent_create\">\n"
" Click to add a personal note.\n"
" </p><p>\n"
" Use notes to organize personal tasks or notes. All\n"
" notes are private; no one else will be able to see them. "
"However\n"
" you can share some notes with other people by inviting "
"followers\n"
" on the note. (Useful for meeting minutes, especially if\n"
" you activate the pad feature for collaborative writings).\n"
" </p><p>\n"
" You can customize how you process your notes/tasks by adding,\n"
" removing or modifying columns.\n"
" </p>\n"
" "
msgstr ""
#. module: note
#: model:note.stage,name:note.demo_note_stage_01
#: model:note.stage,name:note.note_stage_01
msgid "Today"
msgstr "Tänään"
#. module: note
#: model:ir.model,name:note.model_res_users
msgid "Users"
msgstr "Käyttäjät"
#. module: note
#: view:note.note:0
msgid "í"
msgstr "í"
#. module: note
#: view:note.stage:0
msgid "Stage of Notes"
msgstr "Muistiinpanojenvaiheet"
#. module: note
#: field:note.note,message_unread:0
msgid "Unread Messages"
msgstr "Lukemattomat viestit"
#. module: note
#: field:note.note,current_partner_id:0
msgid "unknown"
msgstr ""
#. module: note
#: view:note.note:0
msgid "By sticky note Category"
msgstr "Muistilaput ryhmittäin"
#. module: note
#: help:note.note,message_unread:0
msgid "If checked new messages require your attention."
msgstr "Jos valittu, uudet viestit vaativat huomiosi."
#. module: note
#: field:note.stage,name:0
msgid "Stage Name"
msgstr "Vaiheen nimi"
#. module: note
#: field:note.note,message_is_follower:0
msgid "Is a Follower"
msgstr "on seuraaja"
#. module: note
#: model:note.stage,name:note.demo_note_stage_02
msgid "Tomorrow"
msgstr "Huomenna"
#. module: note
#: view:note.note:0
#: field:note.note,open:0
msgid "Active"
msgstr "Aktiivinen"
#. module: note
#: help:note.stage,user_id:0
msgid "Owner of the note stage."
msgstr "Muistiinpanon vaiheen omistaja."
#. module: note
#: model:ir.ui.menu,name:note.menu_notes_stage
msgid "Categories"
msgstr "Ryhmät"
#. module: note
#: view:note.note:0
#: field:note.note,stage_id:0
msgid "Stage"
msgstr "Vaihe"
#. module: note
#: field:note.tag,name:0
msgid "Tag Name"
msgstr "Tunnisteen nimi"
#. module: note
#: field:note.note,message_ids:0
msgid "Messages"
msgstr "Viestit"
#. module: note
#: view:base.config.settings:0
#: model:ir.actions.act_window,name:note.action_note_note
#: model:ir.ui.menu,name:note.menu_note_notes
#: view:note.note:0
#: model:note.stage,name:note.note_stage_04
msgid "Notes"
msgstr "Muistiinpanot"
#. module: note
#: model:note.stage,name:note.demo_note_stage_03
#: model:note.stage,name:note.note_stage_03
msgid "Later"
msgstr "Myöhemmin"
#. module: note
#: model:ir.model,name:note.model_note_stage
msgid "Note Stage"
msgstr "Muistiinpanon vaihe"
#. module: note
#: field:note.note,message_summary:0
msgid "Summary"
msgstr "Yhteenveto"
#. module: note
#: field:note.note,stage_ids:0
msgid "Stages of Users"
msgstr "Käyttäjien vaiheet"
#. module: note
#: field:note.note,name:0
msgid "Note Summary"
msgstr "Muistiinpanon yhteenveto"
#. module: note
#: model:ir.actions.act_window,name:note.action_note_stage
#: view:note.note:0
msgid "Stages"
msgstr "Vaiheet"
#. module: note
#: help:note.note,message_ids:0
msgid "Messages and communication history"
msgstr "Viesti- ja kommunikointihistoria"
#. module: note
#: view:note.note:0
msgid "Delete"
msgstr "Poista"
#. module: note
#: field:note.note,color:0
msgid "Color Index"
msgstr "Väri-indeksi"
#. module: note
#: field:note.note,sequence:0
#: field:note.stage,sequence:0
msgid "Sequence"
msgstr "Järjestysluku"
#. module: note
#: view:note.note:0
#: field:note.note,tag_ids:0
msgid "Tags"
msgstr "Tunnisteet"
#. module: note
#: view:note.note:0
msgid "Archive"
msgstr "Arkisto"
#. module: note
#: field:base.config.settings,module_note_pad:0
msgid "Use collaborative pads (etherpad)"
msgstr "Käytä yhteistyöhön tauluja (Etherpad)"
#. module: note
#: help:note.note,message_summary:0
msgid ""
"Holds the Chatter summary (number of messages, ...). This summary is "
"directly in html format in order to be inserted in kanban views."
msgstr ""
"Sisältää viestien yhteenvedon (viestien määrän,...). Tämä yhteenveto on "
"valmiiksi html-muodossa, jotta se voidaan viedä kanban näkymään."
#. module: note
#: field:base.config.settings,group_note_fancy:0
msgid "Use fancy layouts for notes"
msgstr ""
#. module: note
#: field:note.note,current_partner_id:0
#: field:note.stage,user_id:0
msgid "Owner"
msgstr "Omistaja"
#. module: note
#: help:note.stage,sequence:0
msgid "Used to order the note stages"
msgstr "Käytetään järjestämään muistiinpanon vaiheet"
#. module: note
#: field:note.note,date_done:0
msgid "Date done"
msgstr "Valmis pvm."
#. module: note
#: field:note.stage,fold:0
msgid "Folded by Default"
msgstr "Tyhjää ei näytetä"

View File

@ -72,12 +72,6 @@ class note_note(osv.osv):
def onclick_note_not_done(self, cr, uid, ids, context=None):
return self.write(cr, uid, ids, {'open': True}, context=context)
#used for undisplay the follower if it's the current user
def _get_my_current_partner(self, cr, uid, ids, name, args, context=None):
user = self.pool.get('res.users').browse(cr, uid, uid, context=context)
pid = user.partner_id and user.partner_id.id or False
return dict.fromkeys(ids, pid)
#return the default stage for the uid user
def _get_default_stage_id(self,cr,uid,context=None):
ids = self.pool.get('note.stage').search(cr,uid,[('user_id','=',uid)], context=context)
@ -101,6 +95,7 @@ class note_note(osv.osv):
'name': fields.function(_get_note_first_line,
string='Note Summary',
type='text', store=True),
'user_id': fields.many2one('res.users', 'Owner'),
'memo': fields.html('Note Content'),
'sequence': fields.integer('Sequence'),
'stage_id': fields.function(_get_stage_per_user,
@ -113,9 +108,9 @@ class note_note(osv.osv):
'date_done': fields.date('Date done'),
'color': fields.integer('Color Index'),
'tag_ids' : fields.many2many('note.tag','note_tags_rel','note_id','tag_id','Tags'),
'current_partner_id' : fields.function(_get_my_current_partner, type="many2one", relation='res.partner', string="Owner"),
}
_defaults = {
'user_id': lambda self, cr, uid, ctx=None: uid,
'open' : 1,
'stage_id' : _get_default_stage_id,
}

View File

@ -49,7 +49,6 @@
<field name="open"/>
<field name="memo"/>
<field name="date_done"/>
<field name="current_partner_id"/>
<field name="message_follower_ids"/>
<field name="tag_ids"/>
<templates>
@ -82,7 +81,7 @@
<field name="tag_ids"/>
<div class="oe_right">
<t t-foreach="record.message_follower_ids.raw_value" t-as="follower">
<img t-if="record.current_partner_id.raw_value!=follower" t-att-src="kanban_image('res.partner', 'image_small', follower)" width="24" height="24" class="oe_kanban_avatar" t-att-data-member_id="follower"/>
<img t-att-src="kanban_image('res.partner', 'image_small', follower)" width="24" height="24" class="oe_kanban_avatar" t-att-data-member_id="follower"/>
</t>
</div>
<div class="oe_clear"></div>

View File

@ -1,23 +1,30 @@
<?xml version="1.0"?>
<openerp>
<data>
<record id="note_note_rule_global" model="ir.rule">
<field name="name">Only followers can access a sticky notes</field>
<field ref="model_note_note" name="model_id"/>
<field name="domain_force">[('message_follower_ids','=',user.partner_id.id)]</field>
<field eval="True" name="global"/>
<field eval="1" name="perm_unlink"/>
<field eval="0" name="perm_write"/>
<field eval="1" name="perm_read"/>
<field eval="0" name="perm_create"/>
</record>
<record id="note_note_rule_global" model="ir.rule">
<field name="name">Only followers can access a sticky notes</field>
<field name="model_id" ref="model_note_note"/>
<field name="domain_force">['|', ('user_id', '=', user.id), ('message_follower_ids', '=', user.partner_id.id)]</field>
<field name="global" eval="True"/>
<field name="perm_create" eval="False"/>
<field name="perm_unlink" eval="False"/>
</record>
<record id="note_note_create_unlink_global" model="ir.rule">
<field name="name">note: create / unlink: responsible</field>
<field name="model_id" ref="model_note_note"/>
<field name="domain_force">[('user_id', '=', user.id)]</field>
<field name="global" eval="True"/>
<field name="perm_write" eval="False"/>
<field name="perm_read" eval="False"/>
</record>
<record id="note_stage_rule_global" model="ir.rule">
<field name="name">Each user have his stage name</field>
<field name="model_id" ref="model_note_stage"/>
<field name="domain_force">['|',('user_id','=',False),('user_id','=',user.id)]</field>
<field name="global" eval="True"/>
</record>
<record id="note_stage_rule_global" model="ir.rule">
<field name="name">Each user have his stage name</field>
<field ref="model_note_stage" name="model_id"/>
<field name="domain_force">['|',('user_id','=',False),('user_id','=',user.id)]</field>
<field eval="True" name="global"/>
</record>
</data>
</openerp>

View File

@ -69,7 +69,7 @@ class pos_config(osv.osv):
'currency_id' : fields.function(_get_currency, type="many2one", string="Currency", relation="res.currency"),
'iface_self_checkout' : fields.boolean('Self Checkout Mode',
help="Check this if this point of sale should open by default in a self checkout mode. If unchecked, OpenERP uses the normal cashier mode by default."),
'iface_cashdrawer' : fields.boolean('Cashdrawer',help="Automatically open the cashdrawer"),
'iface_cashdrawer' : fields.boolean('Cashdrawer', help="Automatically open the cashdrawer"),
'iface_payment_terminal' : fields.boolean('Payment Terminal', help="Enables Payment Terminal integration"),
'iface_electronic_scale' : fields.boolean('Electronic Scale', help="Enables Electronic Scale integration"),
'iface_vkeyboard' : fields.boolean('Virtual KeyBoard', help="Enables an integrated Virtual Keyboard"),
@ -1305,7 +1305,7 @@ class product_product(osv.osv):
'income_pdt': fields.boolean('Point of Sale Cash In', help="Check if, this is a product you can use to put cash into a statement for the point of sale backend."),
'expense_pdt': fields.boolean('Point of Sale Cash Out', help="Check if, this is a product you can use to take cash from a statement for the point of sale backend, example: money lost, transfer to bank, etc."),
'available_in_pos': fields.boolean('Available in the Point of Sale', help='Check if you want this product to appear in the Point of Sale'),
'to_weight' : fields.boolean('To Weight', help="Check if the product should be weighted (mainly used with self check-out interface)."),
'to_weight' : fields.boolean('To Weigh', help="Check if the product should be weighted (mainly used with self check-out interface)."),
}
_defaults = {

View File

@ -116,8 +116,8 @@
<p class="oe_view_nocontent_create">
Click to create a new order.
</p><p>
Use this menu to browse your preceeding orders. To record new
orders, you should better use the menu <i>Your Session</i> for
Use this menu to browse previous orders. To record new
orders, you may use the menu <i>Your Session</i> for
the touchscreen interface.
</p>
</field>
@ -979,7 +979,7 @@
currencies in your cash registers at the beginning and the end
of each session.
</p><p>
Note that you should better to use the menu <i>Your Session</i>
Note that you may use the menu <i>Your Session</i>
to quickly open a new session.
</p>
</field>

View File

@ -0,0 +1,137 @@
# Finnish translation for openobject-addons
# Copyright (c) 2014 Rosetta Contributors and Canonical Ltd 2014
# This file is distributed under the same license as the openobject-addons package.
# FIRST AUTHOR <EMAIL@ADDRESS>, 2014.
#
msgid ""
msgstr ""
"Project-Id-Version: openobject-addons\n"
"Report-Msgid-Bugs-To: FULL NAME <EMAIL@ADDRESS>\n"
"POT-Creation-Date: 2012-12-21 17:06+0000\n"
"PO-Revision-Date: 2014-02-19 10:26+0000\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: Finnish <fi@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Launchpad-Export-Date: 2014-02-20 05:14+0000\n"
"X-Generator: Launchpad (build 16916)\n"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "here:"
msgstr ""
#. module: web_linkedin
#: field:sale.config.settings,api_key:0
msgid "API Key"
msgstr ""
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/js/linkedin.js:331
#, python-format
msgid "No results found"
msgstr "Haku ei tuottanut tuloksia."
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/js/linkedin.js:62
#, python-format
msgid "Ok"
msgstr ""
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "Log into LinkedIn."
msgstr "Kirjaudun LinkedIn:iin."
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/xml/linkedin.xml:13
#, python-format
msgid "People"
msgstr "Henkilöt"
#. module: web_linkedin
#: model:ir.model,name:web_linkedin.model_sale_config_settings
msgid "sale.config.settings"
msgstr ""
#. module: web_linkedin
#: field:sale.config.settings,server_domain:0
msgid "unknown"
msgstr "tuntematon"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "https://www.linkedin.com/secure/developer"
msgstr ""
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/xml/linkedin.xml:15
#, python-format
msgid "Companies"
msgstr "Yritykset"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "API key"
msgstr ""
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "Copy the"
msgstr ""
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/js/linkedin.js:263
#, python-format
msgid "LinkedIn search"
msgstr "LinkedIn-haku"
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/xml/linkedin.xml:31
#, python-format
msgid ""
"LinkedIn access was not enabled on this server.\n"
" Please ask your administrator to configure it in Settings > "
"Configuration > Sales > Social Network Integration."
msgstr ""
#. module: web_linkedin
#: view:sale.config.settings:0
msgid ""
"To use the LinkedIn module with this database, an API Key is required. "
"Please follow this procedure:"
msgstr ""
#. module: web_linkedin
#. openerp-web
#: code:addons/web_linkedin/static/src/js/linkedin.js:60
#, python-format
msgid "LinkedIn is not enabled"
msgstr "LinkedIn ei ole vahvistettu käyttöön"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "Add a new application and fill the form:"
msgstr "Lisää uusi hakemus ja täytä lomake:"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "Go to this URL:"
msgstr "Siirry tähän URL-osoitteeseen:"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "The programming tool is Javascript"
msgstr "Ohjelmointityökalu on JavaScript"
#. module: web_linkedin
#: view:sale.config.settings:0
msgid "JavaScript API Domain:"
msgstr "JavaScript API Toimialue:"

View File

@ -87,7 +87,10 @@ def slug(value):
else:
# assume name_search result tuple
id, name = value
return "%s-%d" % (slugify(name), id)
slugname = slugify(name)
if not slugname:
return str(id)
return "%s-%d" % (slugname, id)
def urlplus(url, params):
return werkzeug.Href(url)(params or None)

View File

@ -1,5 +1,5 @@
# -*- coding: utf-8 -*-
import test_converter
#import test_requests
import test_requests
import test_ui
import test_views

View File

@ -0,0 +1,35 @@
# -*- coding: utf-8 -*-
import unittest2
class URLCase(unittest2.TestCase):
"""
URLCase moved out of test_requests, otherwise discovery attempts to
instantiate and run it
"""
def __init__(self, user, url, source, result):
super(URLCase, self).__init__()
self.user = user
self.url = url
self.source = source
self.result = result
@property
def username(self):
return self.user or "Anonymous Coward"
def __str__(self):
if self.source:
return "%s (from %s, as %s)" % (self.url, self.source, self.username)
return "%s (as %s)" % (self.url, self.username)
__repr__ = __str__
def shortDescription(self):
return ""
def runTest(self):
code = self.result.getcode()
self.assertIn(
code, xrange(200, 300),
"Fetching %s as %s returned an error response (%d)" % (
self.url, self.username, code))

View File

@ -1,5 +1,4 @@
# -*- coding: utf-8 -*-
import collections
import urlparse
import unittest2
import urllib2
@ -9,41 +8,10 @@ import lxml.html
from openerp import tools
import cases
__all__ = ['load_tests', 'CrawlSuite']
class URLCase(unittest2.TestCase):
"""
URLCase moved out of test_requests, otherwise discovery attempts to
instantiate and run it
"""
def __init__(self, user, url, source, result):
super(URLCase, self).__init__()
self.user = user
self.url = url
self.source = source
self.result = result
@property
def username(self):
return self.user or "Anonymous Coward"
def __str__(self):
if self.source:
return "%s (from %s, as %s)" % (self.url, self.source, self.username)
return "%s (as %s)" % (self.url, self.username)
__repr__ = __str__
def shortDescription(self):
return ""
def runTest(self):
code = self.result.getcode()
self.assertIn(
code, xrange(200, 300),
"Fetching %s as %s returned an error response (%d)" % (
self.url, self.username, code))
class RedirectHandler(urllib2.HTTPRedirectHandler):
"""
HTTPRedirectHandler is predicated upon HTTPErrorProcessor being used and
@ -96,12 +64,12 @@ class CrawlSuite(unittest2.TestSuite):
# blow up in multidb situations
self.opener.open('http://localhost:{port}/web/?db={db}'.format(
port=tools.config['xmlrpc_port'],
db=werkzeug.url_quote_plus(tools.config['db_name']),
db=werkzeug.urls.url_quote_plus(tools.config['db_name']),
))
if user is not None:
url = 'http://localhost:{port}/login?{query}'.format(
port=tools.config['xmlrpc_port'],
query=werkzeug.url_encode({
query=werkzeug.urls.url_encode({
'db': tools.config['db_name'],
'login': user,
'key': password,
@ -149,7 +117,7 @@ class URL(object):
self.source = source
def to_case(self, user, result):
return URLCase(user, self.url, self.source, result)
return cases.URLCase(user, self.url, self.source, result)
def load_tests(loader, base, _):
base.addTest(CrawlSuite())

View File

@ -1,22 +1,11 @@
import os
import openerp
inject = [
("openerp.website.Tour", os.path.join(os.path.dirname(__file__), '../static/src/js/website.tour.js')),
("openerp.website.Tour.LoginEdit", os.path.join(os.path.dirname(__file__), "../static/src/js/website.tour.test.admin.js")),
]
import openerp.tests
class TestUi(openerp.tests.HttpCase):
def test_01_pubic_homepage(self):
self.phantom_js("/", "console.log('ok')", "openerp.website.snippet");
def test_02_public_login_logout(self):
# Page injection works but i suspect multiple files doesnt
return
self.phantom_js("/", "openerp.website.Tour.run_test('login_edit')", "openerp.website.Tour", inject=inject);
def test_01_public_homepage(self):
self.phantom_js("/", "console.log('ok')", "openerp.website.snippet")
def test_03_admin_homepage(self):
self.phantom_js("/", "console.log('ok')", "openerp.website.editor", login='admin');
self.phantom_js("/", "console.log('ok')", "openerp.website.editor", login='admin')
def test_04_admin_tour_banner(self):
self.phantom_js("/", "openerp.website.Tour.run_test('banner')", "openerp.website.Tour", login='admin')

View File

@ -17,7 +17,7 @@
<field name="website_path"
on_change="on_change_website_path(website_path, xml_id, context)"
attrs="{'invisible': ['|', ('website_published', '!=', True), ('state', '!=', 'code')]}"/>
<field name="website_url" readonly="1"
<field name="website_url" readonly="1" widget="url"
attrs="{'invisible': ['|', ('website_published', '!=', True), ('state', '!=', 'code')]}"/>
</xpath>
</data>

View File

@ -1,4 +1,4 @@
import openerp
import openerp.tests
class TestUi(openerp.tests.HttpCase):
def test_admin(self):

View File

@ -1,4 +1,4 @@
import openerp
import openerp.tests
class TestUi(openerp.tests.HttpCase):
def test_admin(self):

View File

@ -1,4 +1,4 @@
import openerp
import openerp.tests
inject = [
"./../../../website/static/src/js/website.tour.test.js",

View File

@ -1,6 +1,8 @@
import os
import openerp
import unittest2
import openerp.tests
inject = [
("openerp.website.Tour", os.path.join(os.path.dirname(__file__), '../../website/static/src/js/website.tour.js')),
@ -9,19 +11,15 @@ inject = [
class TestUi(openerp.tests.HttpCase):
def test_01_admin_shop_tour(self):
# Works locally probably due to a race condition on openerp.website.Tour.Shop
# object should only be define once ready
return
self.phantom_js("/", "openerp.website.Tour.run_test('shop')", "openerp.website.Tour.Shop", login="admin")
def test_02_admin_checkout(self):
return
self.phantom_js("/", "openerp.website.Tour.run_test('shop_buy_product')", "openerp.website.Tour", login="admin")
@unittest2.expectedFailure
def test_03_demo_checkout(self):
return
self.phantom_js("/", "openerp.website.Tour.run_test('shop_buy_product')", "openerp.website.Tour.ShopTest", login="demo", inject=inject)
@unittest2.expectedFailure
def test_04_public_checkout(self):
return
self.phantom_js("/", "openerp.website.Tour.run_test('shop_buy_product')", "openerp.website.Tour.ShopTest", inject=inject)